<p>Starting kubernetes 1.20 there has been a change regarding <code>ownerReferences</code> and how K8s performs GC.
Basically if a resource in <code>x</code> namespace spins up a pod/job in a <code>y</code> namespace with child having <code>ownerReferences</code> referencing to parent resource in <code>x</code>, K8s terminates the child pod/job.</p>
<p><a href="https://github.com/kubernetes/kubernetes/blob/master/CHANGELOG/CHANGELOG-1.20.md" rel="nofollow noreferrer">Reference</a>:</p>
<blockquote>
<ul>
<li>Resolves non-deterministic behavior of the garbage collection controller when ownerReferences with incorrect data are encountered. Events with a reason of OwnerRefInvalidNamespace are recorded when namespace mismatches between child and owner objects are detected. The kubectl-check-ownerreferences tool can be run prior to upgrading to locate existing objects with invalid ownerReferences.
<ul>
<li>A namespaced object with an ownerReference referencing a uid of a namespaced kind which does not exist in the same namespace is now consistently treated as though that owner does not exist, and the child object is deleted.</li>
<li>A cluster-scoped object with an ownerReference referencing a uid of a namespaced kind is now consistently treated as though that owner is not resolvable, and the child object is ignored by the garbage collector. (#92743, @liggitt) [SIG API Machinery, Apps and Testing]</li>
</ul>
</li>
</ul>
</blockquote>
<p>If we remove the <code>ownerReferences</code>, the resource wont be garbage collected. Is there a way to deal with this situation i.e.; how to make <code>ownerReferences</code> work in multiple namespaces OR let the job/pod clean itself once completed? Thanks.</p>

<p>As per <a href="https://github.com/kubernetes/kubernetes/pull/92743#issuecomment-729701767" rel="nofollow noreferrer">Fix GC uid races and handling of conflicting ownerReferences #92743
</a></p>
<blockquote>
<p>namespaces are intended to be independent of each other, so cross-namespace references have not been permitted in things like ownerReferences, secret/configmap volume references, etc.</p>
<p>additionally, granting permissions to namespace a is not generally intended to provide visibility or ability to interact with objects from namespace b (or cause system controllers to interact with objects from namespace b).</p>
</blockquote>
<p>and
<a href="https://github.com/kubernetes/website/pull/25091/files" rel="nofollow noreferrer">Update GC cross-namespace note #25091</a></p>
<blockquote>
<p>Cross-namespace owner references are disallowed by design.</p>
</blockquote>
<p>So, using <code>ownerReferences</code> for garbage collection across namespaces is not possible <em>by desing</em>.</p>
<hr />
<p>However, you can emulate multi-namespace GC using labels. You just need to configure those labels when some object creates sub-object.</p>
<p>Alternatively you can delete a namespace to GC all object in that namespace, but that's probably suboptimal solution.</p>
<hr />
<p><strong>EDIT</strong></p>
<pre><code>$ kubectl label pods owner=my -l region=europe
$ kubectl label pods owner=my -l region=pacific
</code></pre>
<pre><code>$ kubectl label svc owner=my -l svc=europe
$ kubectl label svc owner=my -l svc=pacific
</code></pre>
<pre><code>$ kubectl label pod kube-proxy-2wpz2 owner=my -n kube-system 
$ kubectl label pod kube-proxy-cpqxt  owner=my -n kube-system 
</code></pre>
<pre><code>$ kubectl get pods,svc -l owner=my --show-labels --all-namespaces

NAMESPACE     NAME                   READY   STATUS        RESTARTS   AGE    LABELS
default       pod/aloha-pod          1/1     Running       0          54d    app=aloha,owner=my,region=pacific
default       pod/ciao-pod           1/1     Running       0          54d    app=ciao,owner=my,region=europe
default       pod/hello-pod          1/1     Terminating   0          54d    app=hello,owner=my,region=europe
default       pod/ohayo-pod          1/1     Running       0          54d    app=ohayo,owner=my,region=pacific
kube-system   pod/kube-proxy-2wpz2   1/1     Running       2          299d   controller-revision-hash=5cf956ffcf,k8s-app=kube-proxy,owner=my,pod-template-generation=1
kube-system   pod/kube-proxy-cpqxt   1/1     Running       3          299d   controller-revision-hash=5cf956ffcf,k8s-app=kube-proxy,owner=my,pod-template-generation=1

NAMESPACE   NAME              TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)   AGE   LABELS
default     service/europe    ClusterIP   10.109.5.102    &lt;none&gt;        80/TCP    54d   owner=my,svc=europe
default     service/pacific   ClusterIP   10.99.255.196   &lt;none&gt;        80/TCP    54d   owner=my,svc=pacific
</code></pre>
<pre><code>$ kubectl delete pod,svc -l owner=my --dry-run --all-namespaces

pod &quot;aloha-pod&quot; deleted (dry run)
pod &quot;ciao-pod&quot; deleted (dry run)
pod &quot;hello-pod&quot; deleted (dry run)
pod &quot;ohayo-pod&quot; deleted (dry run)
pod &quot;kube-proxy-2wpz2&quot; deleted (dry run)
pod &quot;kube-proxy-cpqxt&quot; deleted (dry run)
service &quot;europe&quot; deleted (dry run)
service &quot;pacific&quot; deleted (dry run)
</code></pre>
<p>Alternatively there could be a bash script that deletes all objects whose controller object doesn't exist, based on labels. It could also run inside the cluster with proper service account configured.</p>
<hr />
<p>There is no straightforward, built-in option to achieve what you want. You should keep <em>owner referenced</em> objects in the same namespace.</p>
