Repository navigation
v1.21.0
Highlights
grpccalls methods with the Connect protocol, and calls streaming methods.grpckeeps to--read-onlyand--allow-host.- Each action declares the kinds of guard it keeps to. An external action does so in
action.yml, which also takesparamsforprobe check. - The external actions graphql and jmap have reference pages.
- For library users:
actionrpc.Guard.Keepingis replaced byKeeps.
gRPC over the Connect protocol
The grpc action can now call a method with the Connect protocol instead of gRPC. The call is a POST over HTTP, so it passes an HTTP/1.1 proxy or load balancer, as the calls of a connect-web client in a browser do.
- name: Get a user
uses: grpc
with:
protocol: connect
addr: https://api.example.com/rpc
service: users.v1.UserService
method: GetUser
body:
id: "123"
test: res.status_code == "OK" && res.body.user.name != ""addris the URL the service is served under; the call goes to<addr>/<service>/<method>. A host and port without a scheme is taken ashttp, orhttpswithtls: true.codecisjson(the default) orproto. Withoutprotofiles, a JSON body is sent as written andservicemust be the full name;codec: protoneedsproto.metadatais sent as headers, andtimeoutis also sent asConnect-Timeout-Ms. Redirects are not followed.reshas the same fields as for a gRPC call. A Connect error gives its gRPC code, such asNOT_FOUND; a response without one, such as a proxy's 502 page, gives the code implied by the HTTP status, such asUNAVAILABLE, as a result rather than an action error.- Server reflection is not used with
protocol: connect.
See Connect Protocol.
gRPC streaming methods
The grpc action now calls methods that stream their requests or their responses, by gRPC and by protocol: connect, with the same parameters as a method that does not stream. The call sends every request, closes its side, and then reads the responses.
- name: Watch users
uses: grpc
with:
method: WatchUsers
body:
filter: active
max_messages: 3
test: res.status_code == "" && len(res.messages) == 3 && !res.complete
- name: Import users
uses: grpc
with:
method: ImportUsers
body:
- name: Ada
- name: Grace
test: res.status_code == "OK" && res.body.imported == 2- A list in
bodyis the messages of a stream of requests, in order. One object is the only message, and[]sends none. A list sent to a method that does not stream its requests is an error. - The responses of a stream are in
res.messages, the last one also inres.body.res.completeistruewhen the server ended the stream. max_messagesstops reading after that many responses. The server has then sent no status, sores.status_codeis empty andres.completeisfalse.- A stream that breaks off after some responses returns them with the status it ended with, such as
DEADLINE_EXCEEDED. - A method that streams both ways is refused before anything is sent.
- With
protocol: connect, a streaming method is called only whenprotofiles declare it. Withproto, each message is checked, and a violation names it by index, such as$[1].user.email.
See Streaming Methods.
The grpc action keeps to the guard
The grpc action now runs under --read-only and --allow-host without --allow-action grpc. It refuses a call the guard does not allow before anything is sent, and the step fails with the kind refused.
--allow-hostis checked against the host and port ofaddr, port 443 when none is named.dns:///andpassthrough:///targets are read through, and the DNS server of adns://server/target is checked too, port 53 when none is named. A target that names no host, such asunix:///tmp/grpc.sock, is refused. Withprotocol: connect, the host of the URL is checked, at the port of its scheme when none is named.- Under
--read-only, a method is called only when every definition of it at hand, the server's reflection and the.protofiles ofproto, declaresoption idempotency_level = NO_SIDE_EFFECTS;. A Connect call withoutprotohas no definition and is refused. - The action applies these checks even when
--allow-action grpcis given. Under--read-only, a workflow that ran every grpc step with--allow-action grpcin v1.20.0 now has calls to methods not declaredNO_SIDE_EFFECTSrefused.
See Under a Guard.
Actions declare the guard they keep to
Which actions run under --read-only and --allow-host used to be a fixed list of built-in names in Probe, so an external action was always refused under a guard unless --allow-action named it. Each action now declares the kinds of guard it keeps to, and an external action does so with guard in its action.yml:
name: greet
description: Say hello over HTTP
guard: [read-only, allow-host]
params: [url, name]
runs:
using: binary
url: https://github.com/<owner>/probe-greet/releases/download/v0.1.0/probe-greet_{os}_{arch}
checksums:
linux_amd64: <SHA-256 of probe-greet_linux_amd64>- The kinds are
read-onlyandallow-host. A step runs under a guard only when its action declares every kind the run is under, or when--allow-actionnames it. An unknown kind is ignored. - Probe does not verify a declaration. The guard holds only as far as the external actions a workflow uses keep to what they declare, so review them before running a workflow under a guard.
- The built-in actions keep to the guard as before:
http,db,grpc,embeddedandhellodeclare both kinds. - The refusal now names the missing kinds, such as
does not keep to --read-only and --allow-host, which the run is under. - Probe reads
action.ymlof every external action before the first job, and downloads the executable only for one that the guard lets run. paramslists the keys the action takes inwith.probe checkreports a key that is not listed, in a step'swithand in a job'sdefaults. Withoutparams,withis not checked. Anaction.ymlthatprobe checkcannot read gives a warning.
The new Guard page describes what Probe and the actions each do, the table of what each built-in action refuses (moved from the CLI reference), and how an external action keeps to the guard. The action.yml fields are in External Actions.
Reference pages for graphql and jmap
The external actions graphql and jmap now have reference pages, in English and Japanese, and probe guide graphql and probe guide jmap print them. Both repositories moved to mozership; the docs and examples now pin these:
uses: github.com/mozership/probe-graphql@ad456d1eefd30a63d14b49c730e5239c4749b34b # v0.1.1
uses: github.com/mozership/probe-jmap@295701f5263fffd64161a34dd377722ccad3923a # v0.1.0- probe-graphql v0.1.1 is the same action as v0.1.0, released from mozership/probe-graphql, and its
action.ymldownloads the executables from there. - The
action.ymlof neither release declaresguardyet, so both are still refused under a guard unless--allow-actionnames them. probe-jmap refuses what the guard does not allow when it is told the guard.
For library users
This release breaks the Go API; workflow files are not affected. actionrpc.Guard.Keeping []string is replaced by Keeps map[string][]string, the kinds of guard each action keeps to by its uses, and a Guard built with Keeping: actions.Keeping() is now built with Keeps: actions.Keeps(). Guard.Runs now requires every kind in Guard.Kinds(). In pb.Guard, field 4 is reserved and keeps is field 5. An external action built with an earlier actionrpc still reads the guard it is sent. See CHANGELOG.md for the full table.
New public API:
actionrpc:Guard.Kinds,Guard.Missing,Guard.WithKeeps, and the constantsKindReadOnlyandKindAllowHost.actions.Keeps(), and aKeeps()in each ofdb,embedded,grpc,helloandhttp.actions.Keeping()stays, computed from the declarations.actionref.ManifestgainsGuardandParams;Resolver.Manifestandactionref.ReadManifestread anaction.ymlwithout fetching the executable.probe.CheckOptions.Manifest, whichprobe checksets toactionref.ReadManifestto check an external action'swithagainst itsparams.grpc.RequestStep, andRunStepon the grpc action, which make a call under the guard of the run;grpc.Requeststays and callsRequestStepwithout a guard.
Changelog
- 9245df5 Call a gRPC method with the Connect protocol
- c5bd19d Call streaming methods with gRPC and the Connect protocol
- 5212a1a Check an addr without a scheme as the URL it stands for
- dc37b8e Check the DNS server a dns:// target names against the guard
- a4640a5 Close the connection, keep the timeout header in range, read a reply as JSON
- 446f932 Document graphql and jmap as external actions, apart from the built-in ones
- 2f48226 Keep the grpc action to the guard of a run
- d767575 Let each action declare the guard it keeps to, and document the guard
- abefbbb Merge pull request #347 from mozership/feat/grpc-connect
- 609df22 Merge pull request #348 from mozership/feat/grpc-guard
- e7de25c Merge pull request #349 from mozership/feat/grpc-streaming
- d8ac12f Merge pull request #350 from mozership/docs/external-actions
- deacd73 Merge pull request #351 from mozership/chore/probe-graphql-v0.1.1
- 692a145 Merge pull request #352 from mozership/feat/guard-declared-by-actions
- 1c6a09a Merge pull request #353 from mozership/release/v1.21.0
- 7675e46 Name probe-graphql by its current owner, mozership
- a0edff3 Pin probe-graphql v0.1.1, whose action.yml names mozership
- 7663cab Prepare the changelog for v1.21.0
- 0c22b87 Read an envelope as it comes, send the protocol version, tell a stream that does not fit
- 8ff4441 Replace a declaration the guard came with, and tell local actions apart
- 676edd1 Say once that workflow files are not affected
- c671dfa Say which idempotency_level a refused method has, and where
- f6a9c71 Say 許可 for what a document, a schema or umask allows, too
- 823f9ff Say 許可 for what the guard allows in the Japanese docs