|
| 1 | +# RFC 0196 - Trigger Hooks from Github Service |
| 2 | +* Comments: [#196](https://github.com/taskcluster/taskcluster-rfcs/pull/196) |
| 3 | +* Proposed by: @ahal |
| 4 | + |
| 5 | +# Summary |
| 6 | + |
| 7 | +In addition to scheduling tasks, the Github service will be able to trigger |
| 8 | +hooks that are specified in a project's `.taskcluster.yml` file. |
| 9 | + |
| 10 | +## Motivation |
| 11 | + |
| 12 | +This will give instance administrators a way to provide "shared tasks" that |
| 13 | +specific projects can opt into using without needing to copy / paste a large |
| 14 | +blob of JSON-e. |
| 15 | + |
| 16 | +Specifically in the Firefox-CI instance, it will allow us to define a single |
| 17 | +well tested and maintained Decision task as a hook. Hiding the complexity from |
| 18 | +projects and ensuring all projects are using the most recent and up-to-date |
| 19 | +features. |
| 20 | + |
| 21 | +# Details |
| 22 | + |
| 23 | +A new `hooks` key will be added to the [taskcluster-yml-v1] schema. This key is |
| 24 | +a list, where each item is an object containing `hookId` and optionally |
| 25 | +additional `context`. Hook ID corresponds to an existing hook in the |
| 26 | +Taskcluster instance, and `context` is a JSON serializable object that gets |
| 27 | +forwarded as part of the payload in the [triggerHook] API. Taskcluster Github |
| 28 | +will always implicitly include the following in the payload: |
| 29 | + |
| 30 | +- `event` - the raw Github event object |
| 31 | +- `now` - the current time, as a string |
| 32 | +- `taskcluster_root_url` - the root URL of the Taskcluster deployment |
| 33 | +- `tasks_for` - the Github event type |
| 34 | + |
| 35 | +For example: |
| 36 | + |
| 37 | +```yml |
| 38 | +version: 1 |
| 39 | +hooks: |
| 40 | + - hookId: decision/taskgraph |
| 41 | + context: |
| 42 | + trustDomain: mozilla |
| 43 | +``` |
| 44 | +
|
| 45 | +In this example, Taskcluster Github would make a call like: |
| 46 | +
|
| 47 | +``` |
| 48 | +triggerHook("decision", "taskgraph", { |
| 49 | + |
| 50 | + "context": { |
| 51 | + "trustDomain": "mozilla" |
| 52 | + }, |
| 53 | + "event": <github event object> |
| 54 | + "now": <timestamp>, |
| 55 | + "taskcluster_root_url": "https://tc.example.com", |
| 56 | + "tasks_for": "github-push", |
| 57 | +}) |
| 58 | +``` |
| 59 | + |
| 60 | +## Permissions |
| 61 | + |
| 62 | +Taskcluster Github will create a `hooks` client with scopes limited to the role |
| 63 | +assumed earlier on based on the repository and Github event type. The role for |
| 64 | +the current repo and context must have sufficient scopes to trigger the hook. |
| 65 | +This works similarly to how Taskcluster Github currently calls the `createTask` |
| 66 | +endpoint. |
| 67 | + |
| 68 | +## Error Handling |
| 69 | + |
| 70 | +If a `hookId` references a hook that does not exist, Taskcluster Github |
| 71 | +will skip that hook and comment on the commit or pull request with an error. |
| 72 | + |
| 73 | +If the `triggerHook` call fails, i.e due to a failure rendering the hook's |
| 74 | +JSON-e body or a scope error, then Taskcluster Github will skip that hook and |
| 75 | +comment on the commit or pull request with details of the failure. |
| 76 | + |
| 77 | +In both cases, Taskcluster Github will not abort and will proceed with firing any |
| 78 | +remaining hooks or scheduling remaining tasks. |
| 79 | + |
| 80 | +## Github Builds |
| 81 | + |
| 82 | +The `triggerHook` API returns the hook task's `taskId` as part of the response. |
| 83 | +Taskcluster Github will use this `taskId` to create a record in the Github |
| 84 | +builds table. This will allow Taskcluster Github to add the task to Github's |
| 85 | +checks UI and keep it updated with status changes. |
| 86 | + |
| 87 | +This logic already exists for tasks scheduled based on the `tasks` key, so the |
| 88 | +only new piece is obtaining the `taskId` from the `triggerHook` response rather |
| 89 | +than parsing it out of the task definition. |
| 90 | + |
| 91 | +## Edge Cases |
| 92 | + |
| 93 | +If the `hooks` and `tasks` keys are both present in the `.taskcluster.yml`, the |
| 94 | +hooks will be processed first, followed by the tasks. |
| 95 | + |
| 96 | +If the hook's JSON-e template renders to `null`, then the hook service doesn't |
| 97 | +create a task. In this case Taskcluster Github does not log any errors nor add |
| 98 | +any records to the Github builds table. |
| 99 | + |
| 100 | +# Implementation |
| 101 | + |
| 102 | +<Once the RFC is decided, these links will provide readers a way to track the |
| 103 | +implementation through to completion, and to know if they are running a new |
| 104 | +enough version to take advantage of this change. It's fine to update this |
| 105 | +section using short PRs or pushing directly to master after the RFC is |
| 106 | +decided> |
| 107 | + |
| 108 | +* <link to tracker bug, issue, etc.> |
| 109 | +* <...> |
| 110 | +* Implemented in Taskcluster version ... |
| 111 | + |
| 112 | +[taskcluster-yml-v1]: https://docs.taskcluster.net/docs/reference/integrations/github/taskcluster-yml-v1 |
| 113 | +[triggerHook]: https://docs.taskcluster.net/docs/reference/core/hooks/api#triggerHook |
0 commit comments