diff --git a/lib/modules/manager/gradle/parser/common.spec.ts b/lib/modules/manager/gradle/parser/common.spec.ts
index c2742363c049a73da6f16d175cccb645750cbbf3..9b2c2339dead2f86061f862ebd6cabb9d1845294 100644
--- a/lib/modules/manager/gradle/parser/common.spec.ts
+++ b/lib/modules/manager/gradle/parser/common.spec.ts
@@ -1,9 +1,10 @@
 import type { lexer } from 'good-enough-parser';
 import { partial } from '../../../../../test/util';
-import type { Ctx, PackageVariables } from '../types';
+import type { Ctx } from '../types';
 import {
   cleanupTempVars,
   coalesceVariable,
+  findVariable,
   increaseNestingDepth,
   interpolateString,
   loadFromTokenMap,
@@ -112,8 +113,17 @@ describe('modules/manager/gradle/parser/common', () => {
     expect(ctx.varTokens).toStrictEqual([{ value: 'foo.bar.baz.qux' }]);
   });
 
+  it('findVariable', () => {
+    ctx.globalVars = {
+      foo: { key: 'foo', value: 'bar' },
+    };
+
+    expect(findVariable('unknown-global-var', ctx)).toBeUndefined();
+    expect(findVariable('foo', ctx)).toStrictEqual(ctx.globalVars['foo']);
+  });
+
   it('interpolateString', () => {
-    expect(interpolateString([], {})).toBeEmptyString();
+    expect(interpolateString([], ctx)).toBeEmptyString();
     expect(
       interpolateString(
         partial<lexer.Token>([
@@ -121,6 +131,7 @@ describe('modules/manager/gradle/parser/common', () => {
           { type: 'symbol', value: 'bar' },
           { type: 'string-value', value: 'baz' },
         ]),
+        ctx,
         {
           bar: { key: '', value: 'BAR' },
         }
@@ -129,13 +140,13 @@ describe('modules/manager/gradle/parser/common', () => {
     expect(
       interpolateString(
         partial<lexer.Token>([{ type: 'symbol', value: 'foo' }]),
-        partial<PackageVariables>()
+        ctx
       )
     ).toBeNull();
     expect(
       interpolateString(
         partial<lexer.Token>([{ type: '_', value: 'foo' }]),
-        partial<PackageVariables>()
+        ctx
       )
     ).toBeNull();
   });
diff --git a/lib/modules/manager/gradle/parser/common.ts b/lib/modules/manager/gradle/parser/common.ts
index 4693da32c294f67440dfcd6b5488c58ac7e2b87f..43a1032311811d49a1a93cb131487b70ceda27a8 100644
--- a/lib/modules/manager/gradle/parser/common.ts
+++ b/lib/modules/manager/gradle/parser/common.ts
@@ -1,7 +1,12 @@
 import { lexer, parser, query as q } from 'good-enough-parser';
 import { clone } from '../../../../util/clone';
 import { regEx } from '../../../../util/regex';
-import type { Ctx, NonEmptyArray, PackageVariables } from '../types';
+import type {
+  Ctx,
+  NonEmptyArray,
+  PackageVariables,
+  VariableData,
+} from '../types';
 
 export const REGISTRY_URLS = {
   google: 'https://dl.google.com/android/maven2/',
@@ -114,9 +119,18 @@ export function coalesceVariable(ctx: Ctx): Ctx {
   return ctx;
 }
 
+export function findVariable(
+  name: string,
+  ctx: Ctx,
+  variables: PackageVariables = ctx.globalVars
+): VariableData | undefined {
+  return variables[name];
+}
+
 export function interpolateString(
   childTokens: lexer.Token[],
-  variables: PackageVariables
+  ctx: Ctx,
+  variables: PackageVariables = ctx.globalVars
 ): string | null {
   const resolvedSubstrings: string[] = [];
   for (const childToken of childTokens) {
@@ -124,7 +138,7 @@ export function interpolateString(
     if (type === 'string-value') {
       resolvedSubstrings.push(childToken.value);
     } else if (type === 'symbol') {
-      const varData = variables[childToken.value];
+      const varData = findVariable(childToken.value, ctx, variables);
       if (varData) {
         resolvedSubstrings.push(varData.value);
       } else {
diff --git a/lib/modules/manager/gradle/parser/handlers.ts b/lib/modules/manager/gradle/parser/handlers.ts
index 972322435b479f2e8159f76c8edcd8e63f640548..4ffbb70a0e319ed01fd273926f0092e693257313 100644
--- a/lib/modules/manager/gradle/parser/handlers.ts
+++ b/lib/modules/manager/gradle/parser/handlers.ts
@@ -11,6 +11,7 @@ import {
   ANNOYING_METHODS,
   GRADLE_PLUGINS,
   REGISTRY_URLS,
+  findVariable,
   interpolateString,
   loadFromTokenMap,
 } from './common';
@@ -32,7 +33,7 @@ export function handleAssignment(ctx: Ctx): Ctx {
     delete ctx.tokenMap.templateStringTokens;
   } else if (valTokens[0].type === 'symbol') {
     // foo = bar || foo = "${bar}"
-    const varData = ctx.globalVars[valTokens[0].value];
+    const varData = findVariable(valTokens[0].value, ctx);
     if (varData) {
       ctx.globalVars[key] = { ...varData };
     }
@@ -62,7 +63,7 @@ export function handleAssignment(ctx: Ctx): Ctx {
 export function handleDepString(ctx: Ctx): Ctx {
   const stringTokens = loadFromTokenMap(ctx, 'templateStringTokens');
 
-  const templateString = interpolateString(stringTokens, ctx.globalVars);
+  const templateString = interpolateString(stringTokens, ctx);
   if (!templateString) {
     return ctx;
   }
@@ -76,7 +77,7 @@ export function handleDepString(ctx: Ctx): Ctx {
   let fileReplacePosition: number | undefined;
   for (const token of stringTokens) {
     if (token.type === 'symbol') {
-      const varData = ctx.globalVars[token.value];
+      const varData = findVariable(token.value, ctx);
       if (varData) {
         packageFile = varData.packageFile;
         fileReplacePosition = varData.fileReplacePosition;
@@ -118,8 +119,8 @@ export function handleKotlinShortNotationDep(ctx: Ctx): Ctx {
   const moduleNameTokens = loadFromTokenMap(ctx, 'artifactId');
   const versionTokens = loadFromTokenMap(ctx, 'version');
 
-  const moduleName = interpolateString(moduleNameTokens, ctx.globalVars);
-  const versionValue = interpolateString(versionTokens, ctx.globalVars);
+  const moduleName = interpolateString(moduleNameTokens, ctx);
+  const versionValue = interpolateString(versionTokens, ctx);
   if (!moduleName || !versionValue) {
     return ctx;
   }
@@ -141,7 +142,7 @@ export function handleKotlinShortNotationDep(ctx: Ctx): Ctx {
     // = template string with multiple variables
     dep.skipReason = 'unknown-version';
   } else if (versionTokens[0].type === 'symbol') {
-    const varData = ctx.globalVars[versionTokens[0].value];
+    const varData = findVariable(versionTokens[0].value, ctx);
     if (varData) {
       dep.groupName = varData.key;
       dep.currentValue = varData.value;
@@ -162,9 +163,9 @@ export function handleLongFormDep(ctx: Ctx): Ctx {
   const artifactIdTokens = loadFromTokenMap(ctx, 'artifactId');
   const versionTokens = loadFromTokenMap(ctx, 'version');
 
-  const groupId = interpolateString(groupIdTokens, ctx.globalVars);
-  const artifactId = interpolateString(artifactIdTokens, ctx.globalVars);
-  const version = interpolateString(versionTokens, ctx.globalVars);
+  const groupId = interpolateString(groupIdTokens, ctx);
+  const artifactId = interpolateString(artifactIdTokens, ctx);
+  const version = interpolateString(versionTokens, ctx);
   if (!groupId || !artifactId || !version) {
     return ctx;
   }
@@ -179,7 +180,7 @@ export function handleLongFormDep(ctx: Ctx): Ctx {
     // = template string with multiple variables
     dep.skipReason = 'unknown-version';
   } else if (versionTokens[0].type === 'symbol') {
-    const varData = ctx.globalVars[versionTokens[0].value];
+    const varData = findVariable(versionTokens[0].value, ctx);
     if (varData) {
       dep.groupName = varData.key;
       dep.managerData = {
@@ -233,7 +234,7 @@ export function handlePlugin(ctx: Ctx): Ctx {
     // = template string with multiple variables
     dep.skipReason = 'unknown-version';
   } else if (pluginVersion[0].type === 'symbol') {
-    const varData = ctx.globalVars[pluginVersion[0].value];
+    const varData = findVariable(pluginVersion[0].value, ctx);
     if (varData) {
       dep.groupName = varData.key;
       dep.currentValue = varData.value;
@@ -276,7 +277,7 @@ export function handleCustomRegistryUrl(ctx: Ctx): Ctx {
 
   if (ctx.tokenMap.name) {
     const nameTokens = loadFromTokenMap(ctx, 'name');
-    const nameValue = interpolateString(nameTokens, localVariables);
+    const nameValue = interpolateString(nameTokens, ctx, localVariables);
     if (nameValue) {
       localVariables = {
         ...localVariables,
@@ -290,6 +291,7 @@ export function handleCustomRegistryUrl(ctx: Ctx): Ctx {
 
   let registryUrl = interpolateString(
     loadFromTokenMap(ctx, 'registryUrl'),
+    ctx,
     localVariables
   );
   if (registryUrl) {
@@ -314,8 +316,8 @@ export function handleLibraryDep(ctx: Ctx): Ctx {
   const groupIdTokens = loadFromTokenMap(ctx, 'groupId');
   const artifactIdTokens = loadFromTokenMap(ctx, 'artifactId');
 
-  const groupId = interpolateString(groupIdTokens, ctx.globalVars);
-  const artifactId = interpolateString(artifactIdTokens, ctx.globalVars);
+  const groupId = interpolateString(groupIdTokens, ctx);
+  const artifactId = interpolateString(artifactIdTokens, ctx);
   if (!groupId || !artifactId) {
     return ctx;
   }
@@ -331,10 +333,7 @@ export function handleLibraryDep(ctx: Ctx): Ctx {
   };
 
   if (ctx.tokenMap.version) {
-    const version = interpolateString(
-      loadFromTokenMap(ctx, 'version'),
-      ctx.globalVars
-    );
+    const version = interpolateString(loadFromTokenMap(ctx, 'version'), ctx);
     if (version) {
       handleLongFormDep(ctx);
     }
@@ -344,10 +343,7 @@ export function handleLibraryDep(ctx: Ctx): Ctx {
 }
 
 export function handleApplyFrom(ctx: Ctx): Ctx {
-  let scriptFile = interpolateString(
-    loadFromTokenMap(ctx, 'scriptFile'),
-    ctx.globalVars
-  );
+  let scriptFile = interpolateString(loadFromTokenMap(ctx, 'scriptFile'), ctx);
   if (!scriptFile) {
     return ctx;
   }
@@ -355,7 +351,7 @@ export function handleApplyFrom(ctx: Ctx): Ctx {
   if (ctx.tokenMap.parentPath) {
     const parentPath = interpolateString(
       loadFromTokenMap(ctx, 'parentPath'),
-      ctx.globalVars
+      ctx
     );
     if (parentPath && scriptFile) {
       scriptFile = upath.join(parentPath, scriptFile);
@@ -397,7 +393,7 @@ export function handleApplyFrom(ctx: Ctx): Ctx {
 export function handleImplicitGradlePlugin(ctx: Ctx): Ctx {
   const pluginName = loadFromTokenMap(ctx, 'pluginName')[0].value;
   const versionTokens = loadFromTokenMap(ctx, 'version');
-  const versionValue = interpolateString(versionTokens, ctx.globalVars);
+  const versionValue = interpolateString(versionTokens, ctx);
   if (!versionValue) {
     return ctx;
   }
@@ -420,7 +416,7 @@ export function handleImplicitGradlePlugin(ctx: Ctx): Ctx {
     // = template string with multiple variables
     dep.skipReason = 'unknown-version';
   } else if (versionTokens[0].type === 'symbol') {
-    const varData = ctx.globalVars[versionTokens[0].value];
+    const varData = findVariable(versionTokens[0].value, ctx);
     if (varData) {
       dep.groupName = varData.key;
       dep.currentValue = varData.value;