pg gem:'警告:没有为类型“numeric”定义类型转换

时间:2016-01-14 16:45:59

标签: ruby postgresql

我无法从pg gem中获取输入的结果。

require 'pg'                                                            
require_relative 'spec/fixtures/database'                               

client = PG.connect( DB[:pg] )                                            
client.type_map_for_queries = PG::BasicTypeMapForQueries.new(client)    
client.type_map_for_results = PG::BasicTypeMapForResults.new(client)    

client.exec( %|select * from testme;| ) do |query|                        
  query.each {|r| puts r.inspect }                                      
end

该程序提供输出:

Warning: no type cast defined for type "money" with oid 790. Please cast this type explicitly to TEXT to be safe for future changes.
Warning: no type cast defined for type "numeric" with oid 1700. Please cast this type explicitly to TEXT to be safe for future changes.
{"string"=>"thing", "logical"=>true, "cash"=>"£1.23", "reel"=>"2.34", "day"=>#<Date: 2015-12-31 ((2457388j,0s,0n),+0s,2299161j)>, "float"=>3.45}

所以:布尔值和浮点数和日期(和整数)被转换,但不是数字或金钱类型。

任何人都可以告诉我如何“明确地转换类型”,假设我不想为每个表硬编码解决方案吗?

3 个答案:

答案 0 :(得分:3)

对于那些默认情况下想要转换字符串的人来说,这是一个陷阱:

client = PG.connect( DB[:pg] )           

map = PG::BasicTypeMapForResults.new(conn)
map.default_type_map = PG::TypeMapAllStrings.new

client.type_map_for_results = map

答案 1 :(得分:2)

与text-ish字段有同样的问题。通过复制编码器并编辑其OID来解决。

text_coder = client.type_map_for_results.coders.find { |c| c.name == 'text' }
new_coder = text_coder.dup.tap { |c| c.oid = 19 } # oid from the warning
conn.type_map_for_results.add_coder(new_coder)

我如何到达那里:如果问题相似但不完全相同,下一个人可能会感兴趣。

我在线阅读其他人谈论type_map_for_results,但他们怎么不知道如何定义编码器。由于在我的案例中它是一个文本字段,我决定尝试克隆现有的字段。我知道我可以在Rails应用程序中找到文本预设,所以我打开了rails console并搜索了:

adapter = ActiveRecord::Base.connection
connection = adapter.instance_variable_get("@connection")
mapping = connection.type_map_for_results
cd mapping  # my console of choice is `pry`
ls          # spotted a likely getter named `coders`
cd coders   # again
ls          # spotted getter `name` and setter `oid=`

所以我把代码放在解决方案中。试一试,它有效。

找到并不是那么简单,所以我决定退出潜伏者模式并在SO上分享。因此:感谢@Andreyy带我进入:)

[pry cd and ls]

答案 2 :(得分:-1)

  1. Google错误消息:“警告:没有为类型”
  2. 定义类型转换
  3. 您可以找到它的来源github
  4. 重新上课,我猜可以使用从150到214的行 例子:
    • public class Xposed implements IXposedHookZygoteInit, IXposedHookLoadPackage { private static int index, indexMax; private static boolean first = true; private static String[] valuesX = {"bla1", "bla2", "bla3", "bla4"}; private Context mCon; private EditText et; @Override public void initZygote(StartupParam startupParam) throws Throwable { findAndHookMethod(TextView.class, "onFocusChanged", boolean.class, int.class, Rect.class, new XC_MethodHook() { @Override protected void afterHookedMethod(MethodHookParam param) throws Throwable { if (param.thisObject instanceof EditText) { et = (EditText) param.thisObject; if ((boolean) param.args[0]) { et.setText("I have focus!!! (1)"); XposedBridge.log("starting quickinsert after focus"); mCon = et.getContext().getApplicationContext(); View.OnKeyListener okl = new View.OnKeyListener() { @Override public boolean onKey(View v, int keyCode, KeyEvent event) { if (event.getAction() == KeyEvent.ACTION_DOWN) { if ((keyCode == KeyEvent.KEYCODE_VOLUME_DOWN || keyCode == KeyEvent.KEYCODE_VOLUME_UP)) { keyPressed(keyCode); return true; } } return false; } };; et.setOnKeyListener(okl); } } } }); } private void keyPressed(int keyCode) { if ((keyCode == KeyEvent.KEYCODE_VOLUME_DOWN)) { if (first) { first = false; } else { if (index < indexMax) { index++; } else { index = 0; } } et.setText(valuesX[index]); XposedBridge.log("keycode down consumed (index " + index + ")"); } else if ((keyCode == KeyEvent.KEYCODE_VOLUME_UP)) { if (first) { first = false; } else { if (index > 0) { index--; } else { index = indexMax; } } et.setText(valuesX[index]); XposedBridge.log("keycode up consumed (index " + index + ")"); } } }
    • register_type 0, 'text', PG::TextEncoder::String
  5. 由于register_type和alias_type是alias_type 0, 'varchar', 'text'的类方法,我只会玩它们,看看是否有任何变化:
    • PG::BasicTypeRegistry::CoderMap
    • PG::BasicTypeRegistry::CoderMap.alias_type 0, 'money', 'text'
  6. 阅读课堂上的评论似乎没有实现这些和其他一些领域的编码/解码。

    您可以考虑使用更高级别的ORM库,例如AvtiveRecord,它可以实现更多类型(money)。