class Veritrans::Tercerog::Mdk::MdkContentHandler

MdkContentHandler クラス

戻り電文(JSON)からレスポンスDTOへプロパティをマッピングするクラス

Constants

DFAULT_ENCODE

デフォルトエンコード

ELEM_OPTION_RESULTS_PATH

決済オプションリザルトエレメントパス

ELEM_RESULT_ROOT

決済コマンド共通部ルートエレメント

SLASH

区切り文字

Public Class Methods

new() click to toggle source

コンストラクタ

# File tgMdk/lib/tg_mdk/mdk_content_handler.rb, line 36
def initialize()
  config = Veritrans::Tercerog::Mdk::MdkConfig.instance
  # DTOの文字エンコードを取得
  @encode = config[:DTO_ENCODE]
end

Public Instance Methods

parse(result_json_string, response_dto) click to toggle source

GW処理結果JSONを解析し、指定した応答Dtoの各プロパティに設定する

@param

result_json_string JSON文字列

@param

response_dto 応答Dto

@return

JSONを設定した応答Dto

# File tgMdk/lib/tg_mdk/mdk_content_handler.rb, line 48
def parse(result_json_string, response_dto)

  hash_data = JSON.parse(result_json_string)

  parse_hash("", hash_data, response_dto, ["#{SLASH}#{ELEM_RESULT_ROOT}"])
  parse_hash("#{SLASH}#{ELEM_RESULT_ROOT}", hash_data[ELEM_RESULT_ROOT], response_dto, ["#{SLASH}#{ELEM_OPTION_RESULTS_PATH}"])
  return response_dto
end

Private Instance Methods

get_attr_accessor_class(obj, attr_accessor_name) click to toggle source

指定したオブジェクトのアクセサメソッドの型を取得する。

@param

obj オブジェクト

@param

attr_accessor_name アクセサメソッド名

@return

アクセサメソッドの型

# File tgMdk/lib/tg_mdk/mdk_content_handler.rb, line 172
def get_attr_accessor_class(obj, attr_accessor_name)

  return nil if obj.nil? || attr_accessor_name.empty?

  if obj.respond_to?(:get_property_class_name_hash) && obj.get_property_class_name_hash["#{attr_accessor_name}"] != nil
    class_name =  obj.get_property_class_name_hash["#{attr_accessor_name}"]
  else
    class_name = attr_accessor_name.gsub(/\b\w/){|word| word.capitalize}
  end
  return nil unless Veritrans::Tercerog::Mdk.const_defined?(class_name)

  class_name = "Veritrans::Tercerog::Mdk::#{class_name}"
  target_class = class_name.split("::").inject(Object){ |c, name| c.const_get(name) }
  if target_class.is_a?(Class)
    return target_class
  end
  return nil
end
parse_hash(parent_path, hash_data, response_dto, ignore_list) click to toggle source

ハッシュデータを指定した応答Dtoの各プロパティに設定する

@param

parent_path 親要素のパス

@param

hash_data ハッシュデータ

@param

response_dto 応答Dto

@param

ignore_list 無視する項目(パス)の配列

@return

JSONを設定した応答Dto

# File tgMdk/lib/tg_mdk/mdk_content_handler.rb, line 65
def parse_hash(parent_path, hash_data, response_dto, ignore_list)

  if hash_data.nil? || !hash_data.is_a?(Hash)
    return response_dto
  end

  if ignore_list.nil? || !ignore_list.is_a?(Array)
    ignore_paths = []
  else
    ignore_paths = ignore_list
  end

  hash_data.each_pair do |key, value|
    current_path = "#{parent_path}#{SLASH}#{key}"
    if ignore_paths.include?(current_path)
      next
    end

    # Element名よりsetter名生成
    setter_name = key.gsub(/\b\w/){|word| word.downcase}.gsub(/[A-Z]/){|word|
      "_".concat word.downcase}
    setter_name = setter_name.concat "="

    # インスタンス変数の存在確認
    if response_dto.respond_to?(setter_name)
      # valueのクラスによって処理を変更
      if value.nil?
        response_dto.send(setter_name, nil)

      elsif value.is_a?(String)
        # valueが文字列の場合
        response_dto.send(setter_name, Veritrans::Tercerog::Mdk::MdkUtils::mdk_encode_to(@encode, value.to_s))

      elsif value.is_a?(Numeric)
        # valueが数値型の場合
        response_dto.send(setter_name, Veritrans::Tercerog::Mdk::MdkUtils::mdk_encode_to(@encode, value.to_s))

      elsif !!value == value
        # valueがBoolean型の場合
        response_dto.send(setter_name, Veritrans::Tercerog::Mdk::MdkUtils::mdk_encode_to(@encode, value.to_s))

      elsif value.is_a?(Hash)
        # valueがハッシュの場合
        attr_class =  get_attr_accessor_class(response_dto, key)
        unless attr_class.nil?
          instance = attr_class.new
          # 処理中ノードとDtoクラスを基に再帰処理を実行
          parse_hash(current_path, value, instance, ignore_list)
          # オブジェクトをDTOプロパティに設定
          response_dto.send(setter_name, instance)
        end
      elsif value.is_a?(Array)
        # valueが配列の場合
        if value.empty?
          # 要素が存在しない場合
          response_dto.send(setter_name, [])
          next
        end

        # keyから型を特定
        attr_class = get_attr_accessor_class(response_dto, key)
        if attr_class.nil?
          # 型が特定できない場合
          array_instance = []

          value.each do |element|
            if !element.nil?
              array_instance << Veritrans::Tercerog::Mdk::MdkUtils::mdk_encode_to(@encode, element.to_s)
            end
          end
          # オブジェクト配列をDTOプロパティに設定
          response_dto.send(setter_name, array_instance)

        else
          # 配列の要素が上記以外の配列の場合
          instance_list = []

          value.each do |element|
            if !element.nil?
              instance = attr_class.new
              # 処理中ノードとDtoクラスを基に再帰処理を実行
              parse_hash(current_path, element, instance, ignore_list)
            instance_list << instance
            end
          end
        # オブジェクト配列をDTOプロパティに設定
        response_dto.send(setter_name, instance_list)
        end
      end
    else
      # パースするプロパティが無かったエレメント要素の存在をログ出力
      getter_name = key.gsub(/\b\w/){|word| word.downcase}.gsub(/[A-Z]/){|word|
        "_".concat word.downcase}
      Veritrans::Tercerog::Mdk::logger.info("attr_accessor: '#{getter_name}' not exists.")
    end
  end

  return response_dto
end