From 0ec3f799ddba168ef5ee8089a7f1d8faf49ccc62 Mon Sep 17 00:00:00 2001 From: Richard Feldman Date: Sat, 28 Oct 2023 21:45:03 -0400 Subject: [PATCH] Update interactive example --- www/wip_new_website/InteractiveExample.roc | 14 +++++++------- www/wip_new_website/content/index.md | 4 ++-- www/wip_new_website/static/site.css | 2 +- 3 files changed, 10 insertions(+), 10 deletions(-) diff --git a/www/wip_new_website/InteractiveExample.roc b/www/wip_new_website/InteractiveExample.roc index 98310f8d58..e1b22970c9 100644 --- a/www/wip_new_website/InteractiveExample.roc +++ b/www/wip_new_website/InteractiveExample.roc @@ -28,29 +28,29 @@ view = sectionsToStr [ Desc [Comment "Click anything here to see an explanation.Tap anything here to\n# see an explanation."] "

Comments in Roc begin with a # and go to the end of the line.

", Newline, - Desc [Ident "main", Kw "="] "

This begins the definition of main, which is where our program will begin.

In Roc, assignments are always constant, which means writing main = again in the same scope would give an error.

", + Desc [Ident "main", Kw "="] "

This defines main, which is where our program will begin.

In Roc, all definitions are constant, so writing main = again in the same scope would give an error.

", Indent, - Desc [Ident "Path.fromStr", Str "\"url.txt\""] "

This converts the string \"url.txt\" into a Path by passing it to the Path.fromStr function.

Function arguments are separated with whitespace rather than commas. Parens are only needed in nested function calls.

", + Desc [Ident "Path.fromStr", Str "\"url.txt\""] "

This converts the string \"url.txt\" into a Path by passing it to Path.fromStr.

Function arguments are separated with whitespace. Parentheses are only needed in nested function calls.

", Newline, - Desc [Kw "|>", Ident "storeEmail"] "

The pipe operator (|>) is syntax sugar for passing the previous answer to the next function in the “pipeline.”

So far this pipeline desugars to:

storeEmail\n    (Path.fromStr \"url.txt\")

The next |> continues the pipeline.

", + Desc [Kw "|>", Ident "storeEmail"] "

The pipe operator (|>) is syntax sugar for passing the previous value to the next function in the “pipeline.”

Here, we're taking the value returned by Path.fromStr \"url.txt\" and passing it to storeEmail.

The next |> continues the pipeline.

", Newline, - Desc [Kw "|>", Ident "Task.onErr", Ident "handleErr"] "

If the task returned by the previous step in the pipeline fails, pass its error to handleErr.

The whole pipeline now desugars to:

Task.onErr\n    (storeEmail …)\n    handleErr

It creates a Path from a string, then stores an email based on that path, then handles any errors that happened.

", + Desc [Kw "|>", Ident "Task.onErr", Ident "handleErr"] "

If the task returned by the previous step in the pipeline fails, pass its error to handleErr.

The pipeline essentially does this:

val1 = Path.fromStr \"url.txt\"\nval2 = storeEmail val1\n\nTask.onErr val2 handleErr

It creates a Path from a string, stores an email based on that path, and then does error handling.

", Outdent, Newline, Desc [Ident "storeEmail", Kw "=", Lambda ["filename"]] "

This defines a function named storeEmail.

In Roc, functions are ordinary values, so we assign names to them using = like with any other value.

The \\arg1, arg2 -> syntax begins a function, and the part after -> is the function's body.

", Indent, - Desc [Ident "url", Kw "<-", Ident "File.readUtf8", Ident "filename", Kw "|>", Ident "Task.await"] "

This reads the contents of the file (as a UTF-8 string) into url.

The <- operator does backpassing, which is syntax sugar for defining a function. This whole line desugars to:

Task.await\n    (File.readUtf8 filename)\n    \\url ->

The lines after this one form the body of the \\url -> callback function, which runs if the file read succeeds.

", + Desc [Ident "url", Kw "<-", Ident "File.readUtf8", Ident "filename", Kw "|>", Ident "Task.await"] "

This reads the contents of the file (as a UTF-8 string) into url.

The <- does backpassing, which is syntax sugar for defining a function. This whole line desugars to:

Task.await\n    (File.readUtf8 filename)\n    \\url ->

The lines after this one form the body of the \\url -> callback, which runs if the file read succeeds.

", Newline, Desc [Literal "{", Ident "name", Literal ",", Ident "email", Literal "}"] "

This is record destructuring syntax.

It takes ", Desc [Kw "<-", Ident "Http.get", Ident "url", Ident "Json.codec"] "

TODO Json.codec, type inference, early error

", Desc [Kw "|>", Ident "Task.await"] "

TODO Task.await

", Newline, - Desc [Ident "dest", Kw "=", Str "\"\\(name).txt\""] "

The \\(name) will be replaced in the string with the contents of name. This is called string interpolation.

Note that there's no |> Task.await on this line. Earlier lines needed that because they were I/O tasks, but this line is an ordinary assignment, so there's no task to await.

", + Desc [Ident "dest", Kw "=", Str "\"\\(name).txt\""] "

The \\(name) in this string literal will be replaced with the value in name. This is string interpolation.

Note that this line doesn't end with |> Task.await. Earlier lines needed that because they were I/O tasks, but this is a plain old definition, so there's no task to await.

", Newline, Desc [Literal "_"] "

In Roc, if you don’t want to bother naming something, you can always choose the name _.

You can name as many things as you like _, even in the same scope, but you can’t reference anything named _.

So it’s only useful for when you don’t want to choose a name.

", Desc [Kw "<-", Ident "File.writeUtf8", Ident "(Path.fromStr dest)", Ident "email", Kw "|>", Ident "Task.await"] "

This writes the email string to the file encoded as UTF-8.

The parentheses here show where the nested call to Path.fromStr begins and ends.

", Newline, - Desc [Ident "Stdout.line", Str "\"Wrote email to \\(dest)\""] "

Note that there’s no |> Task.await here, like there were after earlier tasks.

That’s because, although Stdout.line does return a task, we don’t need to await it because nothing else happens after it.

", + Desc [Ident "Stdout.line", Str "\"Wrote email to \\(dest)\""] "

This prints what we did to stdout.

Note that this line doesn't end with |> Task.await. That’s because, although Stdout.line returns a task, we don’t need to await it because nothing happens after it.

", Outdent, Newline, Desc [Ident "handleErr", Kw "=", Lambda ["err"]] "

Like storeEmail, handleErr is also a function.

Although type annotations are optional everywhere in Roc—because the language has 100% type inference—you could add type annotations to main, storeEmail, and handleErr if you wanted to.

", diff --git a/www/wip_new_website/content/index.md b/www/wip_new_website/content/index.md index 34a35d0924..754e3711ce 100644 --- a/www/wip_new_website/content/index.md +++ b/www/wip_new_website/content/index.md @@ -70,7 +70,7 @@ You can try out Roc right now using this read-eval-print loop (REPL), which runs ## Use Cases -Roc is a very new language (it doesn’t even have a numbered release yet, just nightly builds!) but it can already be used for several things if you’re up for being an early adopter—with all the bugs and missing features which come with that territory. +Roc is a very young language (it doesn’t even have a numbered release yet, just nightly builds!) but it can already be used for several things if you’re up for being an early adopter—with all the bugs and missing features which come with that territory. Currently these use cases are the best-supported: @@ -89,7 +89,7 @@ You can create your own! Learn about **platforms and applications**... ## Larger Example Here’s a larger example that shows a few different aspects of Roc: -* File I/O and HTTP +* File I/O and HTTP requests * Pattern matching for error handling * JSON deserialization via type inference * Common syntax sugar: string interpolation, pipelines, and backpassing diff --git a/www/wip_new_website/static/site.css b/www/wip_new_website/static/site.css index 2a8487e1f5..b3d0278db5 100644 --- a/www/wip_new_website/static/site.css +++ b/www/wip_new_website/static/site.css @@ -813,7 +813,7 @@ code .dim { .interactive-desc { display: none; background-color: #ddd; - padding: 8px 16px; + padding: 0 16px; margin-top: 9px; }