{"record":{"id":"e7d9cee5e223ef18","repo":"dbt-labs/dbt-core","slug":"argument-name-to-has-var-has-incompatible-type","errorCode":null,"errorMessage":"argument 'name' to has_var() has incompatible type; value is not a string","messagePattern":"argument 'name' to has_var\\(\\) has incompatible type; value is not a string","errorType":"validation","errorClass":"minijinja::Error (InvalidOperation)","httpStatus":null,"severity":"error","filePath":"crates/dbt-jinja-vars/src/var.rs","lineNumber":121,"sourceCode":"            format!(\n                \"Required var '{}' not found in config:\\nVars supplied to {} = {}\",\n                var_name,\n                package_name,\n                serde_json::to_string_pretty(vars_lookup).unwrap()\n            ),\n        )\n    }\n\n    /// Common handler for `has_var`.\n    fn call_has_var(&self, state: &State<'_, '_>, args: &[Value]) -> Result<Value, Error> {\n        if args.is_empty() {\n            return Err(Error::new(\n                ErrorKind::InvalidOperation,\n                \"has_var requires 1 argument\",\n            ));\n        }\n        let var_name = args[0].as_str().ok_or_else(|| {\n            Error::new(\n                ErrorKind::InvalidOperation,\n                \"argument 'name' to has_var() has incompatible type; value is not a string\",\n            )\n        })?;\n        let present = self.contains_var(state, var_name)?;\n        Ok(Value::from(present))\n    }\n\n    /// Common implementation for `Object::call`.\n    fn call_impl(\n        self: &Arc<Self>,\n        state: &State<'_, '_>,\n        args: &[Value],\n        _listeners: &[Rc<dyn RenderingEventListener>],\n    ) -> Result<Value, Error> {\n        let (var_name, default_value) = Self::parse_args(args)?;\n        self.call_as_function(state, var_name, default_value)\n    }","sourceCodeStart":103,"sourceCodeEnd":139,"githubUrl":"https://github.com/dbt-labs/dbt-core/blob/0267ce9170576975b76b64ce856b2e5848e96617/crates/dbt-jinja-vars/src/var.rs#L103-L139","documentation":"Type guard in DbtJinjaVars::call_has_var: the first positional argument to has_var() must be a variable name, but the supplied Jinja value is not a string, so it cannot name a var to look up. The at-fault input is the argument passed to has_var() in the template.","triggerScenarios":"Calling `{{ has_var(42) }}`, `{{ has_var(some_var_value) }}` where the value is not a string, or passing a dict/list of candidate names.","commonSituations":"Passing the var's value instead of its name (confusing `has_var(my_var)` with checking the value); numeric column names used as var keys; dynamically built names not coerced to strings.","solutions":["Quote the name: `has_var('my_var')`.","Coerce dynamic names with the `| string` filter: `has_var(key | string)`.","Ensure you pass the lookup key, not the value you expect it to hold."],"exampleFix":"// before (Jinja)\n{% if has_var(warehouse_id) %}\n// after\n{% if has_var('warehouse_id') %}","handlingStrategy":"type-guard","validationCode":"{% if candidate is not string %}{{ exceptions.raise_compiler_error('has_var name must be a string') }}{% endif %}","typeGuard":"// Jinja\n{% macro safe_has_var(name) %}\n  {% if name is not string %}{{ return(false) }}{% endif %}\n  {{ return(has_var(name | string)) }}\n{% endmacro %}","tryCatchPattern":null,"preventionTips":["Pass quoted literal names: has_var('name')","Coerce dynamic names with | string before calling","Do not confuse the var name (key) with its value"],"tags":["jinja","type-error","has-var","dbt"],"backgroundTag":"invalid-argument-value","analyzedSha":"0267ce9170576975b76b64ce856b2e5848e96617","analyzedAt":"2026-09-07T21:53:39.732Z","contentChangedAt":"2026-09-07T21:53:39.732Z","schemaVersion":2},"datasetVersion":"2026-09-14T16:17:12.679Z"}