project Websites / Gitlab Issue Listing Script avatar

websites/Gitlab-Issue-Listing-Script#15: public_projects_only can leak internal projects



Issue Information

Issue Type: issue
Status: closed
Reported By: btasker

Milestone: v0.3
Created: 21-Oct-21 22:52



Description

Currently, the public_projects_only config flag only causes us to drop privileges when collecting the initial project list.

If a public project links to an internal-only one, we'll include that because our API user can access internal projects.

Need to apply this flag more widely - the main exception being when fetching comments/notes: that API (for whatever reason) requires an authenticated user.



Toggle State Changes

Activity


Although not what I was originally thinking of when I raised this issue, whilst working on #19 I found another source of leakage.

The main projects listing is generated by dropping privileges, and iterating over gitlab's paginated result set:

function getProjectList(){
    global $config;

    //https://gitlab.example.com/api/v4/projects

    // Do we include auth? Without it we'll only get public projects
    // with it, we'll get everything the user can access
    $do_auth = (!$config->public_projects_only);

    $url = $config->server . "/api/v4/projects?sort=asc&order_by=name";
    $r = $this->callAPI("GET", $url, false, $do_auth);

    $projects = json_decode($r['result']);
    $project_arr = array();
    $x = 0;
    while (true){
        if (!$projects){
            break;
        }

        foreach ($projects as $project) {

            $p = array(
                "name" => $project->path,
                "namespaced_name" => $project->name_with_namespace,
                "project_key" => $project->path_with_namespace,
                "gitlab_url" => $project->web_url,
                "description" => $project->description,
                "avatar" => $project->avatar_url
            );

            $project_arr[] = $p;
        }

        if (array_key_exists("next", $r['links'])){
            $b = $this->callAPI("GET", GILSUtils::forceHTTPS($r['links']["next"]["link"]));
            $r = $b;
            $projects = json_decode($r['result']);
        }else{
            break;
        }
        $x++;
    }
    return $project_arr;
}

We set $do_auth based on the config flag and pass it into callAPI() to tell it whether to include the auth header.

However, the default behaviour in callAPI() is to do auth, and we're not passing $do_auth into the invocation used to fetch later pages.

So privileges get dropped for the first call, but not subsequent ones - we'll end up including non-public ones.

This is fixed in commit be8572d

mentioned in issue #12

It turns out that this isn't an issue, in fact the opposite is true.

Most of the gitlab calling methods do something like

$r = $this->callAPI("GET", $url, false, false);

So what we've found (in #12) is that the system often cannot display items (commits in that case) which aren't public.

Need to move the auth calculation somewhere public and then update all to use that.

verified

mentioned in commit 234b8dbf93acb61394393e0dac53470a15ee11b7

Commit: 234b8dbf93acb61394393e0dac53470a15ee11b7 
Author: B Tasker                            
                            
Date: 2022-04-18T11:26:42.000+01:00 

Message

Move auth enabled/disabled calcuation to a global point and then make all API calls honour it for websites/Gitlab-Issue-Listing-Script#15

This means that if public_projects_only is set, auth will be disabled and the client won't retrieve nonpublic commits, issues, projects etc

+22 -26 (48 lines changed)

This is fixed - all calls to callAPI() now use $config->do_auth the value of which is calculated in index.php just after instantiating the config object