Skip to content
This repository has been archived by the owner on Apr 4, 2022. It is now read-only.

Sync sponsorships with GitHub webhooks #6

Open
driesvints opened this issue Aug 21, 2021 · 2 comments
Open

Sync sponsorships with GitHub webhooks #6

driesvints opened this issue Aug 21, 2021 · 2 comments
Labels
enhancement New feature or request

Comments

@driesvints
Copy link
Owner

driesvints commented Aug 21, 2021

It would be cool if we could sync incoming GitHub webhooks into a database table so sponsorships can be checked against a persistent storage instead of performing GraphQL API calls.

We could leverage Spatie's https://github.com/spatie/laravel-github-webhooks package for this maybe.

This is atm a pretty vague idea as I'm not sure how practically this would be. Would we only sync sponsorships for the authed user on the client? Or more?

Also see https://docs.github.com/en/developers/webhooks-and-events/webhooks/webhook-events-and-payloads#sponsorship

@driesvints driesvints added the enhancement New feature or request label Aug 21, 2021
@driesvints driesvints changed the title Sync with GitHub webhooks Sync sponsorships with GitHub webhooks Aug 21, 2021
@claudiodekker
Copy link

claudiodekker commented Aug 25, 2021

Posting for relevance / use-for-parts (copied from my WIP inertiajs implementation):

public function organizationIds(): array
{
    $query = <<<'EOF'
        query {
          viewer {
            organizations(first: 100) {
              nodes {
                databaseId
              }
            }
          }
        }
    EOF;

    $response = $this->execute($query);

    return Collection::make(Arr::get($response, 'viewer.organizations.nodes', []))
        ->pluck('databaseId')
        ->all();
}

I personally found databaseId fields to be more (theoretically) reliable than a login, and use that to check against existing sponsors exactly like this ticket describes. Here's the fake test response:

Http::fake([
    'https://api.github.com/graphql' => Http::response([
        'data' => [
            'viewer' => [
                'organizations' => [
                    "nodes" => [
                        ["databaseId" => 958072],
                        ["databaseId" => 39676034],
                        ["databaseId" => 47703742],
                    ]
                ],
            ],
        ],
    ]),
]);

<?php

namespace App\Http\Requests;

use Illuminate\Foundation\Http\FormRequest;

class GithubWebhookRequest extends FormRequest
{
    /**
     * Determine if the user is authorized to make this request.
     *
     * @return bool
     */
    public function authorize()
    {
        $secret = config('services.github.webhook_secret');
        if (is_null($secret)) {
            return true;
        }

        $signature = $this->headers->get('X-Hub-Signature-256', '');
        $hash = 'sha256='.hash_hmac('sha256', (string) $this->getContent(), $secret);

        return hash_equals($hash, $signature);
    }

    /**
     * Get the validation rules that apply to the request.
     *
     * @return array
     */
    public function rules()
    {
        return [
            //
        ];
    }
}
/** @test */
public function it_allows_the_request_when_a_webhook_secret_is_set_and_the_correct_hash_header_is_used(): void
{
    config(['services.github.webhook_secret' => 'secret']);
    $payload = $this->getSponsorsPayload('created');

    $headers = ['X-Hub-Signature-256' => 'sha256='.hash_hmac('sha256', json_encode($payload), 'secret')];
    $this->postJson('/api/github/webhooks/sponsorship', $payload, $headers)
        ->assertStatus(200);

    $this->assertTrue(GithubSponsor::where('github_api_login', 'monalisa')->exists());
}

@claudiodekker
Copy link

I also have a very WIP but functional Github Webhook implementation already.

Let me know if you want it by the time you intend to work on this feature, as by that point I imagine I can provide you either directly with a link the the InertiaJS repo where it's open-sourced, or provide you with an up-to-date sample instead of posting an outdated copy here & forgetting to update it down the line.

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

2 participants