hive的變數傳遞設定

2021-06-29 15:05:15 字數 1871 閱讀 1067

今天同事在oozie的workflow中執行乙個hive查詢,但是直接就報異常:variable substitution depth too large:40,從網上查詢可知,可以確認是由於語句中使用了過多的變數導致,在hive以前的版本中,這個限制是寫死的40個,查詢hive的最新的原**,雖然判斷的位置的提示資訊已經變化,但是原理一樣:

### org.apache.hadoop.hive.ql.parse.variablesubstitution:

public string substitute(hiveconf conf, string expr) 

if (hiveconf.getboolvar(conf, confvars.hivevariablesubstitute)) else

int depth = hiveconf.getintvar(conf, confvars.hivevariablesubstitutedepth);

return substitute(conf, expr, depth);

}

如果開啟hive.variable.substitute(預設開啟),則使用systemvariables的substitute方法和hive.variable.substitute.depth(預設為40)進行進一步的判斷:

protected

final string substitute(configuration conf, string expr, int depth)

string substitute = getsubstitute(conf, var);

if (substitute == null) else

prev = match.end();

}if (!found)

eval = builder.tostring();

}if (s > depth)

return eval;

}

如果使用的${}引數超過hive.variable.substitute.depth的數量,則直接丟擲異常,所以我們在語句的前面直接加上set hive.variable.substitute.depth=100; 問題解決!

set命令的執行是在commandprocessor實現類setprocessor裡具體執行,但是substitute語句同時也會在compileprocessor中呼叫,也就是在hive語句編譯時就呼叫了,所以oozie在使用時呼叫beeline執行語句時,compile階段就報出異常。

但是為什麼hue直接執行這個語句時沒有問題? 因為hue在執行hive時使用的是python開發的beeswax,而beeswax是自己直接處理了這些變數,使用變數實際的值替換變數後再提交給hive執行:

def

substitute_variables

(input_data, substitutions):

""" replaces variables with values from substitutions.

"""deff

(value):

ifnot isinstance(value, basestring):

return value

new_value = template(value).safe_substitute(substitutions)

if new_value != value:

log.debug("substituted %s -> %s" % (repr(value), repr(new_value)))

return new_value

return recursive_walk(f, input_data)

hive變數傳遞的原始碼實現

用過hive的人都知道,可以通過在cli向hive傳遞引數,變數等,這裡其實是通過下面兩個類實現的。1 2 org.apache.hadoop.hive.ql.processors.setprocessor類 org.apache.hadoop.hive.ql.parse.variablesubst...

hive變數傳遞的原始碼實現

用過hive的人都知道,可以通過在cli向hive傳遞引數,變數等,這裡其實是通過下面兩個類實現的。1 2 org.apache.hadoop.hive.ql.processors.setprocessor類 org.apache.hadoop.hive.ql.parse.variablesubst...

python變數傳遞 python變數傳遞

python變數傳遞 數值 num 1 123 num 2 num 1 改變num 2值前 print num 1 num 2 format num 1,num 2 num 2 0 改變num 2值後 print num 1 num 2 format num 1,num 2 輸出num 1 123,...