<p>I'm looking for a way to run <code>kubectl auth can-i get pods --as system:serviceaccount:default:test</code> using kubernetes go-client.</p>
<p>So far I got the below code but it doesn't work as I'm getting a different response in comparison to <code>kubectl auth can-i</code>. I know this is about impersonation and so I'm adding <code>rest.ImpersonationConfig</code> but it's still not working.</p>
<p><strong>Steps to reproduce:</strong></p>
<pre><code>kind create cluster
kubectl create sa test
kubectl create role test --verb=get --verb=list --resource=pods
kubectl create rolebinding test --role=test --serviceaccount=default:test

kubectl auth can-i get pod --as system:serviceaccount:default:test
# yes
</code></pre>
<p><strong>Code:</strong></p>
<pre class="lang-golang prettyprint-override"><code>package main

import (
    &quot;context&quot;
    &quot;fmt&quot;
    &quot;os&quot;

    authv1 &quot;k8s.io/api/authorization/v1&quot;
    metav1 &quot;k8s.io/apimachinery/pkg/apis/meta/v1&quot;
    &quot;k8s.io/client-go/kubernetes&quot;
    &quot;k8s.io/client-go/rest&quot;
    &quot;k8s.io/client-go/tools/clientcmd&quot;
)

func main() {

    kubeconfig := fmt.Sprintf(&quot;%s/.kube/config&quot;, os.Getenv(&quot;HOME&quot;))
    config, err := clientcmd.BuildConfigFromFlags(&quot;&quot;, kubeconfig)
    if err != nil {
        panic(err.Error())
    }

    config.Impersonate = rest.ImpersonationConfig{
        UserName: &quot;system:serviceaccount:default:test&quot;,
    }

    clientset, err := kubernetes.NewForConfig(config)
    if err != nil {
        panic(err.Error())
    }

    action := authv1.ResourceAttributes{
        Namespace: &quot;default&quot;,
        Verb:      &quot;get&quot;,
        Resource:  &quot;pod&quot;,
    }

    selfCheck := authv1.SelfSubjectAccessReview{
        Spec: authv1.SelfSubjectAccessReviewSpec{
            ResourceAttributes: &amp;action,
        },
    }

    resp, err := clientset.AuthorizationV1().
        SelfSubjectAccessReviews().
        Create(context.TODO(), &amp;selfCheck, metav1.CreateOptions{})

    if err != nil {
        panic(err.Error())
    }

    if resp.Status.Allowed {
        fmt.Println(&quot;allowed&quot;)
    } else {
        fmt.Println(&quot;denied&quot;)
    }
}
</code></pre>

<p>I figured it out! I used the singular form of &quot;pod&quot; instead of the plural &quot;pods&quot; in ResourceAttributes.</p>
<pre class="lang-golang prettyprint-override"><code>package main

import (
    &quot;context&quot;
    &quot;fmt&quot;
    &quot;os&quot;

    authv1 &quot;k8s.io/api/authorization/v1&quot;
    metav1 &quot;k8s.io/apimachinery/pkg/apis/meta/v1&quot;
    &quot;k8s.io/client-go/kubernetes&quot;
    &quot;k8s.io/client-go/rest&quot;
    &quot;k8s.io/client-go/tools/clientcmd&quot;
)

func main() {

    kubeconfig := fmt.Sprintf(&quot;%s/.kube/config&quot;, os.Getenv(&quot;HOME&quot;))
    config, err := clientcmd.BuildConfigFromFlags(&quot;&quot;, kubeconfig)
    if err != nil {
        panic(err.Error())
    }

    config.Impersonate = rest.ImpersonationConfig{
        UserName: &quot;system:serviceaccount:default:test&quot;,
    }

    clientset, err := kubernetes.NewForConfig(config)
    if err != nil {
        panic(err.Error())
    }

    action := authv1.ResourceAttributes{
        Namespace: &quot;default&quot;,
        Verb:      &quot;get&quot;,
        Resource:  &quot;pods&quot;,
    }

    selfCheck := authv1.SelfSubjectAccessReview{
        Spec: authv1.SelfSubjectAccessReviewSpec{
            ResourceAttributes: &amp;action,
        },
    }

    resp, err := clientset.AuthorizationV1().
        SelfSubjectAccessReviews().
        Create(context.TODO(), &amp;selfCheck, metav1.CreateOptions{})

    if err != nil {
        panic(err.Error())
    }

    if resp.Status.Allowed {
        fmt.Println(&quot;allowed&quot;)
    } else {
        fmt.Println(&quot;denied&quot;)
    }
}

</code></pre>
