- This journey was made easier with the help of:
- The resulting bot is usubot
- This article’s purpose is to become a tutorial for those who would want to use bot-components
First things first, we need to make sure that we’re able to receive messages from GitHub.
Schematically, we want to do the following thing:
- Start by creating a channel on smee.io
- Install the smee client:
npm install global smee-client
- there are other way that you can find when you create your channel
- Start forwarding any webhooks to your channel to your localhost
smee -u https://smee.io/OHVrxtvcvfBMZGFD --path /event_handler --port 3000
- Don’t stop the client or close the window, this will be helpful for the rest of this journey
- Go on your apps settings page on github and click on create a New Github App
- Fill the Homepage URL with the url provided by smee:
- Fill the Webhook URL with the url provided by smee:
- Create a password to secure your webhook endpoints:
- Give your app the following permissions and subscribe to the following events (you can edit them whenever you want):
- Let the
Only on this account
checked and create your GitHub App - You should be moved to the About page of your app where you’ll need to store:
- The App ID
- Generate a client secret
- Generate a private key (that will be downloaded directly)
Important: Right now you could install your app but since nobody is listening to your opened port, nothing would happen. Let’s fix it immediately
- Clone the tutorial repository or create a new directory with the following structure:
step1 ├── bin │ ├── dune │ └── main.ml └── dune-project
with:
- main.ml:
open Lwt open Cohttp open Cohttp_lwt_unix let server = let callback _conn req body = (* Get the URI *) let uri = req |> Request.uri |> Uri.to_string in (* Get the Request *) let reqs = Request.uri req |> Uri.path in (* Get the Method *) let meth = req |> Request.meth |> Code.string_of_method in (* Get the Headers *) let headers = req |> Request.headers |> Header.to_string in (* Get the body *) Cohttp_lwt.Body.to_string body >>= fun bodys -> Format.printf "@[<v 0>URI: %s@,Req: %s@,Method: %s@,Headers: %s@,Body: %s@,@]@." uri reqs meth headers bodys; Server.respond_string ~status:`OK ~body:bodys () in Server.create ~mode:(`TCP (`Port 3000)) (Server.make ~callback () ~conn_closed:(fun _ -> Format.eprintf "Connection closed@.")) let () = Lwt_main.run server
- dune:
(executable (package ocamlbot-step1) (name main) (public_name ocamlbot-step1) (libraries cohttp-lwt-unix conduit-lwt) )
- dune-project:
(lang dune 2.8) (generate_opam_files true) (name ocamlbot-step1) (version dev) (authors "mattiasdrp") (maintainers "mattiasdrp") (source (github mattiasdrp/ocamlbot-tutorial)) (package (name ocamlbot-step1) (synopsis "OCamlbot, step1") (description "\ First step for an OCaml bot, just read messages on localhost, port 3000") (depends (ocaml (>= 4.10)) (dune (>= 2.2)) (lwt (>= 5.3.0)) (cohttp-lwt (>= 2.5.4)) (cohttp-lwt-unix (>= 2.5.4)) ) )
- main.ml:
- (optional) If you don’t want to potentially spoil your global opam installation,
opam switch create -y .
and go grab a coffee - Go to the
step1
directory if you cloned the project or in your directory if you did it manually opam install -y dune cohttp-lwt-unix conduit-lwt && dune build
dune exec ocamlbot-step1
(don’t stop it)
- Create an empty (private) repository
- Go to the Install App panel and click on install next to your account
- Here you can select all your repositories or select some of them. Select the empty repository you just created
- If you did everything correctly:
- You should see that your smee tab in your terminal received someand received a
200
answer. HTTP Status 200 isOK
. - If you look at your ocamlbot-step1 tab, you should see a lof of informations:
URI: //smee.io/event_handler Req: /event_handler Method: POST Headers: host: smee.io Accept-Encoding: gzip, deflate content-type: application/json [...] Body: { "action": "created", "installation": { ... }, ... } Connection closed
- Your smee channel webpage should have a first event, “installation”, that you can expand and which contains the same content as the one displayed by our simple bot
- You should see that your smee tab in your terminal received someand received a
Since we gave our app the right to send webhooks when an issue is created or commented, create an issue in your empty repo and comment it, two new events should appear (remember to never close the smee channel nor the ocamlbot program running).
Remember our first schema:
Now, we would like to instead execute some actions on the issue that has been opened: