1"use strict";(self.webpackChunkpartners=self.webpackChunkpartners||[]).push([[18264],{15680:(e,t,a)=>{a.d(t,{xA:()=>s,yg:()=>h});var n=a(96540);function r(e,t,a){return t in e?Object.defineProperty(e,t,{value:a,enumerable:!0,configurable:!0,writable:!0}):e[t]=a,e}function o(e,t){var a=Object.keys(e);if(Object.getOwnPropertySymbols){var n=Object.getOwnPropertySymbols(e);t&&(n=n.filter((function(t){return Object.getOwnPropertyDescriptor(e,t).enumerable}))),a.push.apply(a,n)}return a}function i(e){for(var t=1;t<arguments.length;t++){var a=null!=arguments[t]?arguments[t]:{};t%2?o(Object(a),!0).forEach((function(t){r(e,t,a[t])})):Object.getOwnPropertyDescriptors?Object.defineProperties(e,Object.getOwnPropertyDescriptors(a)):o(Object(a)).forEach((function(t){Object.defineProperty(e,t,Object.getOwnPropertyDescriptor(a,t))}))}return e}function l(e,t){if(null==e)return{};var a,n,r=function(e,t){if(null==e)return{};var a,n,r={},o=Object.keys(e);for(n=0;n<o.length;n++)a=o[n],t.indexOf(a)>=0||(r[a]=e[a]);return r}(e,t);if(Object.getOwnPropertySymbols){var o=Object.getOwnPropertySymbols(e);for(n=0;n<o.length;n++)a=o[n],t.indexOf(a)>=0||Object.prototype.propertyIsEnumerable.call(e,a)&&(r[a]=e[a])}return r}var p=n.createContext({}),c=function(e){var t=n.useContext(p),a=t;return e&&(a="function"==typeof e?e(t):i(i({},t),e)),a},s=function(e){var t=c(e.components);return n.createElement(p.Provider,{value:t},e.children)},g="mdxType",y={inlineCode:"code",wrapper:function(e){var t=e.children;return n.createElement(n.Fragment,{},t)}},u=n.forwardRef((function(e,t){var a=e.components,r=e.mdxType,o=e.originalType,p=e.parentName,s=l(e,["components","mdxType","originalType","parentName"]),g=c(a),u=r,h=g["".concat(p,".").concat(u)]||g[u]||y[u]||o;return a?n.createElement(h,i(i({ref:t},s),{},{components:a})):n.createElement(h,i({ref:t},s))}));function h(e,t){var a=arguments,r=t&&t.mdxType;if("string"==typeof e||r){var o=a.length,i=new Array(o);i[0]=u;var l={};for(var p in t)hasOwnProperty.call(t,p)&&(l[p]=t[p]);l.originalType=e,l[g]="string"==typeof e?e:r,i[1]=l;for(var c=2;c<o;c++)i[c]=a[c];return n.createElement.apply(null,i)}return n.createElement.apply(null,a)}u.displayName="MDXCreateElement"},57187:(e,t,a)=>{a.r(t),a.d(t,{assets:()=>p,contentTitle:()=>i,default:()=>y,frontMatter:()=>o,metadata:()=>l,toc:()=>c});var n=a(58168),r=(a(96540),a(15680));const o={id:"configure-webhook",title:"Configure webhook"},i=void 0,l={unversionedId:"docs/workshops/ci-cd-legacy/set-up-ci/configure-webhook",id:"docs/workshops/ci-cd-legacy/set-up-ci/configure-webhook",title:"Configure webhook",description:"When using Pact in a CI/CD pipeline, there are two reasons for a pact verification task to take place:",source:"@site/docs/docs/workshops/ci-cd-legacy/set-up-ci/04_configure_webhook.md",sourceDirName:"docs/workshops/ci-cd-legacy/set-up-ci",slug:"/docs/workshops/ci-cd-legacy/set-up-ci/configure-webhook",permalink:"/docs/workshops/ci-cd-legacy/set-up-ci/configure-webhook",draft:!1,editUrl:"https://github.com/pactflow/docs.pactflow.io/edit/master/website/docs/docs/workshops/ci-cd-legacy/set-up-ci/04_configure_webhook.md",tags:[],version:"current",lastUpdatedBy:"Yousaf Nabi",lastUpdatedAt:1674493712,formattedLastUpdatedAt:"Jan 23, 2023",sidebarPosition:4,frontMatter:{id:"configure-webhook",title:"Configure webhook"},sidebar:"university",previous:{title:"Configure consumer and provider pipelines",permalink:"/docs/workshops/ci-cd-legacy/set-up-ci/configure-consumer-and-provider-pipelines"},next:{title:"Conclusion",permalink:"/docs/workshops/ci-cd-legacy/set-up-ci/conclusion"}},p={},c=[{value:"Expected state by the end of this step",id:"expected-state-by-the-end-of-this-step",level:2}],s={toc:c},g="wrapper";function y(e){let{components:t,...a}=e;return(0,r.yg)(g,(0,n.A)({},s,a,{components:t,mdxType:"MDXLayout"}),(0,r.yg)("p",null,"When using Pact in a CI/CD pipeline, there are two reasons for a pact verification task to take place:"),(0,r.yg)("ul",null,(0,r.yg)("li",{parentName:"ul"},"When the provider changes (to make sure it does not break any existing consumer expectations)"),(0,r.yg)("li",{parentName:"ul"},"When a pact changes (to see if the provider is compatible with the new expectations)")),(0,r.yg)("p",null,"To ensure that the verification step is run whenever a pact changes, we need to configure a PactFlow webhook to trigger a provider verification build in Github Actions. You can see the configuration for this build in ",(0,r.yg)("inlineCode",{parentName:"p"},".github/workflows/verify_changed_pact.yml")," in the provider project. Rather than verifying the pacts with the configured tags, this build just verifies the pact that has changed. This is achieved by passing the URL of the changed pact to the build via a parameter in the body of the webhook request."),(0,r.yg)("p",null,"The PactFlow webhook will need a Github access token to be able to trigger the build in Github. We don't want the Github token to be stored in clear text in the webhook, so we will create a secret in PactFlow to contain token."),(0,r.yg)("ol",null,(0,r.yg)("li",{parentName:"ol"},(0,r.yg)("p",{parentName:"li"},"Create a Github token."),(0,r.yg)("ol",{parentName:"li"},(0,r.yg)("li",{parentName:"ol"},"In Github:",(0,r.yg)("ol",{parentName:"li"},(0,r.yg)("li",{parentName:"ol"},"Open the ",(0,r.yg)("inlineCode",{parentName:"li"},"Personal access tokens page"),(0,r.yg)("ol",{parentName:"li"},(0,r.yg)("li",{parentName:"ol"},"Click on your profile picture in the top right of the window."),(0,r.yg)("li",{parentName:"ol"},"Select ",(0,r.yg)("inlineCode",{parentName:"li"},"Settings")," -> Select ",(0,r.yg)("inlineCode",{parentName:"li"},"Developer settings")," from the bottom of the menu on the left -> Select ",(0,r.yg)("inlineCode",{parentName:"li"},"Personal access tokens")," from the menu on the left."))),(0,r.yg)("li",{parentName:"ol"},"Click ",(0,r.yg)("inlineCode",{parentName:"li"},"Generate new token")),(0,r.yg)("li",{parentName:"ol"},"Set ",(0,r.yg)("inlineCode",{parentName:"li"},"Note")," to ",(0,r.yg)("inlineCode",{parentName:"li"},"Token for triggering example-provider pact verification build")),(0,r.yg)("li",{parentName:"ol"},"Select ",(0,r.yg)("inlineCode",{parentName:"li"},"public_repo")," scope."),(0,r.yg)("li",{parentName:"ol"},"Click ",(0,r.yg)("inlineCode",{parentName:"li"},"Generate token")),(0,r.yg)("li",{parentName:"ol"},"Copy the value of the token and put it in an open file (or better yet, store it in your password manager!)"))))),(0,r.yg)("li",{parentName:"ol"},(0,r.yg)("p",{parentName:"li"},"Create a PactFlow secret for the Github token."),(0,r.yg)("ol",{parentName:"li"},(0,r.yg)("li",{parentName:"ol"},"In your PactFlow account:",(0,r.yg)("ol",{parentName:"li"},(0,r.yg)("li",{parentName:"ol"},"Go to the Secrets page",(0,r.yg)("ol",{parentName:"li"},(0,r.yg)("li",{parentName:"ol"},"Click on the Settings icon in the top left (it looks like a cog wheel) -> Select the ",(0,r.yg)("inlineCode",{parentName:"li"},"Secrets")," tab from the menu on the left."))),(0,r.yg)("li",{parentName:"ol"},'Click "ADD SECRET"'),(0,r.yg)("li",{parentName:"ol"},'Select "None" in the team drop down box.'),(0,r.yg)("li",{parentName:"ol"},"Enter the name ",(0,r.yg)("inlineCode",{parentName:"li"},"githubToken")," and paste the value that you copied in the previous step."),(0,r.yg)("li",{parentName:"ol"},'Click "CREATE"'))))),(0,r.yg)("li",{parentName:"ol"},(0,r.yg)("p",{parentName:"li"},"Create the webhook."),(0,r.yg)("ol",{parentName:"li"},(0,r.yg)("li",{parentName:"ol"},(0,r.yg)("p",{parentName:"li"},"In your PactFlow account:"),(0,r.yg)("ol",{parentName:"li"},(0,r.yg)("li",{parentName:"ol"},(0,r.yg)("p",{parentName:"li"},"Select the ",(0,r.yg)("inlineCode",{parentName:"p"},"Webhooks")," tab from the settings page.")),(0,r.yg)("li",{parentName:"ol"},(0,r.yg)("p",{parentName:"li"},'Click "ADD WEBHOOK".')),(0,r.yg)("li",{parentName:"ol"},(0,r.yg)("p",{parentName:"li"},"Set:"),(0,r.yg)("ul",{parentName:"li"},(0,r.yg)("li",{parentName:"ul"},(0,r.yg)("p",{parentName:"li"},"Team: None")),(0,r.yg)("li",{parentName:"ul"},(0,r.yg)("p",{parentName:"li"},"Description:"),(0,r.yg)("pre",{parentName:"li"},(0,r.yg)("code",{parentName:"pre"},"Pact changed webhook for pactflow-example-provider\n"))),(0,r.yg)("li",{parentName:"ul"},(0,r.yg)("p",{parentName:"li"},'Consumer: leave as "ALL"')),(0,r.yg)("li",{parentName:"ul"},(0,r.yg)("p",{parentName:"li"},"Provider: select ",(0,r.yg)("inlineCode",{parentName:"p"},"pactflow-example-provider"))),(0,r.yg)("li",{parentName:"ul"},(0,r.yg)("p",{parentName:"li"},"Events: select ",(0,r.yg)("inlineCode",{parentName:"p"},"Contract published with changed content or tags"))),(0,r.yg)("li",{parentName:"ul"},(0,r.yg)("p",{parentName:"li"},"URL:"),(0,r.yg)("pre",{parentName:"li"},(0,r.yg)("code",{parentName:"pre",className:"language-bash"},"https://api.github.com/repos/<YOUR GITHUB ACCOUNT HERE>/example-provider/dispatches\n"))),(0,r.yg)("li",{parentName:"ul"},(0,r.yg)("p",{parentName:"li"},"Headers:"),(0,r.yg)("pre",{parentName:"li"},(0,r.yg)("code",{parentName:"pre",className:"language-bash"},"Content-Type: application/json\nAccept: Accept: application/vnd.github.everest-preview+json\nAuthorization: Bearer ${user.githubToken}\n"))),(0,r.yg)("li",{parentName:"ul"},(0,r.yg)("p",{parentName:"li"},"Body:"),(0,r.yg)("pre",{parentName:"li"},(0,r.yg)("code",{parentName:"pre"}
1,'{\n "event_type": "pact_changed",\n "client_payload": {\n "pact_url": "${pactbroker.pactUrl}"\n }\n}\n'))))),(0,r.yg)("li",{parentName:"ol"},(0,r.yg)("p",{parentName:"li"},'Click the "TEST" button and ensure that it runs successfully.'),(0,r.yg)("pre",{parentName:"li"},(0,r.yg)("code",{parentName:"pre"},"\ud83d\udc49 The Github API returns a 404 instead of an authorization error if the token is not correctly set. If you see a 404, it may be that the URL is incorrect, or it may be that the access token is not configured correctly.\n"))),(0,r.yg)("li",{parentName:"ol"},(0,r.yg)("p",{parentName:"li"},'Click the "CREATE" button.')))))),(0,r.yg)("li",{parentName:"ol"},(0,r.yg)("p",{parentName:"li"},"Verify that the pact verification build for the provider is running correctly"),(0,r.yg)("ol",{parentName:"li"},(0,r.yg)("li",{parentName:"ol"},"In Github:",(0,r.yg)("ol",{parentName:"li"},(0,r.yg)("li",{parentName:"ol"},'Open the Github Actions page for the "Verify changed pact" workflow',(0,r.yg)("ol",{parentName:"li"},(0,r.yg)("li",{parentName:"ol"},"Click ",(0,r.yg)("inlineCode",{parentName:"li"},"Actions")," -> Under ",(0,r.yg)("inlineCode",{parentName:"li"},"Workflows"),", select ",(0,r.yg)("inlineCode",{parentName:"li"},"Verify changed pact")))),(0,r.yg)("li",{parentName:"ol"},"Select the latest execution")))))),(0,r.yg)("p",null,"\ud83d\udc49 Each of the above steps can be automated in PactFlow via the PactFlow API - you can see the targets for the commands in the provider's Makefile."),(0,r.yg)("h2",{id:"expected-state-by-the-end-of-this-step"},"Expected state by the end of this step"),(0,r.yg)("ul",null,(0,r.yg)("li",{parentName:"ul"},"Both consumer and provider builds passing \u2705"),(0,r.yg)("li",{parentName:"ul"},"A webhook that has been tested and shown to trigger a pact verification build of the provider.")))}y.isMDXComponent=!0}}]);
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.