@@ -1,566 +1,9 @@
2−title = "Ford"
2+title = "Ford Fusion"
4template = "doc.html"
4template = "doc.html"
5aliases = ["/docs/learn/arvo/ford/"]
5aliases = ["/docs/learn/arvo/ford/"]
7−Our typed and marked computation engine.
9−A variety of different services are provided by `%ford`, but they mostly
8+> This document is out of date as of 2020.07.20. In the meantime, see the [blog
10−involve compiling hook files, slapping/slamming code with marked data,
9+> post](https://urbit.org/blog/ford-fusion/) about Ford Fusion.
11−and converting data between marks, including validating data to a mark.
12−Throughout every computation, `%ford` keeps track of which resources are
13−dependencies so that the client may be aware when one or more
14−dependencies are updated.
16−`%ford` neither accepts unix events nor produces effects. It exists
17−entirely for the benefit of applications and other vanes, in particular
18−`%gall`. `%eyre` exposes the functional publishing aspects of `%ford`
19−while `%gall` uses `%ford` to control the execution of applications.
20−`%clay` is intended to use `%ford` to managed marked data, but this is
25−`%ford` accepts just one card, `%exec`. This is misleading, however,
26−since there are fourteen different `silk`s that may be used with it. In
27−every case, the expected response to a `%exec` card is a `%made` gift
28−with either an error or the produced result along with its set of
31−Silks may autocons, so that the product of a cell of silks is a cell of
32−the product of the two silks.
36−Tries to functionally produce the file at a given beam with the given
37−mark and heel. It fails if there is no way to translate at this level.
41−Functionally produces the file at a given beam with the given mark and
42−heel. If there is no way to translate at this beam, we pop levels off
43−the stack and attempt to bake there until we find a level we can bake.
44−This should almost always be called instead of `%bake`.
48−Slams the result of one silk against the result of another.
52−Translates the given silk to the given mark, if possible. This is one of
53−the critical and fundamental operations of ford.
57−Diffs the two given silks (which must be of the same mark), producing a
58−cage of the mark specified in `++mark` in `++grad` for the mark of the
63−Produces exactly its input. This is rarely used on its own, but many
64−silks are recursively defined in terms of other silks, so we often need
65−a silk that simply produces its input. A monadic return, if you will.
69−Computes the given silk with the given tank as part of the stack trace
74−Produces an error if the cage is empty. Otherwise, it produces the value
79−Takes a silk and a list of changes to make to the silk. At each wing in
80−the list we put the value of the associated silk.
84−Applies the second silk as a patch to the first silk. The second silk
85−must be of the mark specified in `++mark` in `++grad` for the mark of
90−Performs a structured assembly directly. This is not generally directly
91−useful because several other silks perform supersets of this
92−functionality. We don't usually have naked hoods outside ford.
96−Produces a [core](/docs/glossary/core/) containing the entirety of Zuse and Hoon, suitable for
97−running arbitrary code against. The mark is `%noun`.
101−Slaps a hoon against a subject silk. The mark of the result is `%noun`.
105−Validates untyped data from a ship against a given mark. This is an
106−extremely useful function.
110−One of the most common ways to use ford is through ford's runes, all of which begin with `/` ("fas"). A ford rune runs a step of a ford build and places the result in the subject. There are various kinds of build steps, some of which take other build steps as parameters. The most common pattern is to have a sequence of ford runes at the top of a hoon source file that import the results of evaluating other hoon files. This is how we "import a library" in urbit: we add the result of compiling another hoon file into the current subject, possibly renaming it by wrapping a face around it.
112−Another common use case is assembling and rendering markdown templates into a single HTML file, to be sent as an HTTP response in urbit's web server `%eyre`. It's important to keep in mind that %ford is quite flexible and generic, and is used in other parts of urbit -- such as the dojo -- that would not traditionally fall under the purview of a build system.
116−The `/+` rune accepts a filename as an argument. It interprets that filename
117−as a hoon source file within the `lib` directory. This is how we import a shared
120−To run this example, put this code in your desk at `gen/faslus.hoon` and run
121−`+faslus` in your dojo. This example is a generator. For more information on
122−generators, see the [generator docs](@/docs/tutorials/hoon/generators.md).
128−|= {{now/@da * *} $~ $~}
133−produces: `"c.314d"` (or something similar depending on when you run it)
135−You can import multiple libraries with a single `/+` rune by separating them
138−Replace the code in `gen/faslus.hoon` with the following:
141−/+ time-to-id, hep-to-cab
144−|= {{now/@da * *} $~ $~}
146−=/ id (time-to-id now)
147−=/ str "my-id-is-{id}"
148−(hep-to-cab (crip str))
151−This should print something like `my_id_is_c.3588`.
153−Another feature of the
154−`/+` and `/-` runes is the ability to specify the ship and case from which to
160−/+ time-to-id, hep-to-cab/4/~zod
163−will load the `hep-to-cab` library from `~zod` at `%clay` revision `4`.
167−The `/-` rune accepts a filename as an argument. It interprets that filename as
168−a hoon source file within the `sur` directory. The `sur` directory contains
169−shared structures that can be used by other parts of urbit. This is somewhat
170−similar to including a header file in C.
182−`/-` can also take multiple files as arguments, and the ship and case of those
183−arguments can be specified. See the `/+` docs for more details about the syntax
188−`/~ <twig>` produces a "horn" that evaluates a twig and places the product in
189−the subject. Arbitrary hoon can be in the twig. A
191−structure representing a `%ford` static resource.
202−In wide-form, `/~` always takes a tuple (which may be a degenerate tuple of one element), and produces it.
208−produces: `%something`
217−`// <rel-path>` parses `rel-path` as a hoon twig, and then adds the resulting
218−twig to the subject. Note that the result type of this rune is not a horn, but
219−just a hoon twig, so its result can't be used as an argument to other runes
220−that expect a horn. There is no wide-form for this rune.
226−(frobnicate:file-to-include %.n)
228−:: contents of file-to-include.hoon
237−_Note: `%` means current directory, which in a hoon file will resolve to the
238−"directory" containing that file. Also, %clay doesn't have first-class
239−directories the way unix filesystems do. Whereas in unix, a directory is a
240−special kind of file, in %clay it's just a path prefix, and there is no file
241−stored at that path._
245−`/=` runs a horn (usually produced by another ford rune), takes the result of
246−that horn, and wraps a face around it.
256−In wide-form, `/=` uses `=` as a delimiter: `/=foo=/~[a=0 b=1]`
260−`/:` takes a path and a horn, and evaluates the horn with the current path set to the supplied path.
261−`/mar/` renders the mark 'mar' at the current path.
265−/= hoo-source /: /path/to/hoon-file /hoon/
270−produces the text of the hoon file at "/path/to/hoon-file/hoon".
272−`/hoon/` renders the current path using the `%hoon` mark, which in this case
273−passes the contents through unchanged. In general, rendering a file with a
274−mark will potentially run the contents through a series of conversion
275−operations. For details on marks, see the
278−Here's an example that includes a mark conversion:
280−/= page /: /path/to/html/file /mime/
284−:: contents of /path/to/html/file:
285−<html><head><title>My Fascinating Blog</title></head></html>
288−`[[%text %html ~] 60 '<html><head><title>My Fascinating Blog</title></head></html>']`
290−This result includes the MIME type ('text/html'), the content length in bytes,
293−In wide-form, `/:` uses `:` as a delimiter: `/=page=/:/path/to/html/file:/mime/`
295−### `/!mark/` "faszap"
299−/= mime /: /%/some-hoon-file /!mime/
303−:: contents of /%/some-hoon-file:
306−produces: `[[%text %plain ~] 15 'produces-a-cord']`
310−`/&` passes a horn through multiple marks, right-to-left. It has both a
311−wide-form and a tall-form syntax. In wide-form, it takes a series of mark
312−arguments followed by a horn. In tall-form, it takes a single mark followed by
316−/= some-text /: /%/text-file /&mime&/txt/
320−produces: `[[%text %plain ~] p=17 q='Hi I\'m some text\0a']`
322−This example shows two of the ways marks are used. The first way is what
323−happens with the `/txt/` mark: we use it to find a file in clay with that
324−extension, without performing any conversions. Since this file is stored with
325−the `%txt` mark in `%clay`, its type is a `wain`: a list of cords, where each
326−cord is a single line. Once we've read the file, the `%mime` mark converts the
327−`wain` to a triple that includes the MIME type ("text/plain"), the content
328−length in bytes, and the content itself as a cord.
331−/= page /&html&elem&/~[;div.foo;]
335−produces: `'<html><head></head><body><div class="foo"></div></body></html>'`
337−This runs the sail expression `;div.foo;` through the `%elem` mark, then
338−through the `%html` mark. The `/~` rune produces an item of mark `noun`. The
339−`%elem` mark converts the mark of the expression from `noun` to `elem` by
340−checking that the type fits in `manx` (a hoon/sail type indicating an XML
341−element). The `%html` mark recognizes the `%elem` and converts it to an HTML
342−string with enclosing `<html>`, `<head>`, and `<body>` tags.
344−It's possible to use wide-form `/&` with more than two marks, by using `&` as a
345−delimiter between marks and adding a `/` before the last mark, like:
346−`/&d&c&b&/a/`. The last argument here can actually be any arbitrary horn, not
347−just a mark: `/&c&b&/:path:/mark/`
349−Tall-form `/&` takes only two arguments: a mark and a horn. The mark does not
350−need to be enclosed in `/`'s: `/& html /elem/`
354−`/|` takes a series of horns and produces the first one (left-to-right) that
355−succeeds. If none succeed, it produces stack traces from all of its arguments.
359−/= res /: /%/path/to/file
367−tries to parse the file at `/%/path/to/file` as a hoon expression and evaluate
368−it (`/!elem/`), and then if that fails, tries to convert the file to an HTML
369−element directly (`/elem/`). This is used in urbit's `tree` publishing system
370−to enable a user to place either a hoon file or a static file in a directory,
371−and have them both result in webpages, with preference given to treating the
372−file as hoon to be evaluated.
374−Wide-form `/|` encloses its arguments in parentheses, with a single space as a delimiter:
379−`/_` can be used in two ways: filtered and unfiltered.
381−Unfiltered `/_` takes a horn as an argument. It produces a new horn representing the
382−result of mapping the supplied horn over the list of files in the current
383−directory. The keys in the resulting map are the basenames of the files in the
384−directory, and each value is the result of running that horn on the contents of
391−`(map term cord)`kids
394−produces a value of type `(map term cord)`, where each key is the basename (the
395−filename without the prefix), and each value is the result of running the
396−contents of the file through the `%hoon` mark, which validates the
397−hoon code and returns it unmodified. So, the resulting map associates basenames
400−Wide-form unfiltered `/_` doesn't need a delimiter: `/= kids /_/hoon/`
402−### `/_` filtered: run a horn on each file in the directory matching an aura
404−Filtered `/_` takes an aura and a horn, and filters the list of files in the
405−current directory by whether their filenames can be parsed to an [atom](/docs/glossary/atom/) of that
406−aura. It then produces a map where each key is the filename after parsing into
407−that atom type, and each value is the result of running the horn on the
408−contents of that file.
412−/= timed-posts /_ @da /md/
413−`(map @da @t)`timed-posts
415−produces a map from dates to cords. This product will only contain files whose
416−names are parsable into `@da` dates. The values are the file contents converted
417−to a cord of markdown-formatted text.
419−Wide-form filtered `/_` uses `_` as a delimiter: `/= timed-posts /_@da_/md/`
423−`/;` takes a twig and a horn. The twig should evaluate to a [gate](/docs/glossary/gate/), which is then slammed
424−with the result of the horn as its sample.
429− /; |=({a/@ b/@} +(b))
437−Here's a slightly more complex example with runes that use the filesystem:
440− /; |=(a/@t (lent (crip a)))
441− /: /%/path/to/hoon/file /hoon/
445−produces the number of bytes in the file "/%/path/to/hoon/file."
449−`/,` is a switch statement, which picks a branch to evaluate based on
450−whether the current path matches the path in the switch statement.
451−Takes a sequence of pairs of (path, horn) terminated by a `==`. No wide-form.
456− /: /===/right-path :: set path to /%/right-path
459− /another-wrong-path /~ ~
460− /right-path /~ %evaluate-me :: only evaluate this horn
466−produces: `'evaluate-me'`
470−Produce a null-terminated list from a sequence of horns, terminated by a `==`. No wide-form.
487−produces: `[%ames %behn %clay %dill %eyre %ford %gall ~]`.
491−`/^` takes a mold and a horn, and casts the result of the horn to the mold.
495−/= liz /^ (list @) :: cast to real list
496− /~ ~[1 2 3] :: no 'i' or 't' faces
498−?< ?=($~ liz) :: prevent find-fork
504−Without the cast, we wouldn't be able to access the 'i' face of the list.
506−Wide-form `/^` uses `^` as a delimiter: `/^(list @)^/~[1 2 3 ~]`
510−`/#` takes a horn and produces a cell of the dependency
511−hash of the result of the horn, and the result itself.
515−/= inline /^ {dep/@uvH txt/@t} /# /: /%/my-script /js/
517−;= ;script: (trip txt.inline) :: set script contents
518− ;script@"/~/on/{<dep.inline>}.js"; :: set script src
521−produces two `<script>` tags. The first has its contents set to the contents
522−of the JavaScript file we loaded from clay. The second is an auto-update
523−script that polls the server to check whether the dependency hash has changed.
524−This pattern is used in urbit's `tree` web publishing system.
526−Wide-form `/#` does not need a delimiter:
527−`/= inline /^ {dep/@uvH txt/@t} /#/:/%/my-script:/js/`
531−`/$` will slam a gate on whatever extra arguments have been supplied to this build.
532−At the moment, only HTTP requests forwarded by `%eyre` contain any extra arguments,
533−and using this rune outside of that context will cause an error. Requests from `%eyre`
534−contain an argument representing the query string, which can be parsed using the
535−standard library gate `++fuel:html`.
542− %who {<(~(get ju aut.ced.gas) 0)>}
543− %where {(spud s.bem.gas)}
544− %case {(scow %ud p.r.bem.gas)}
547−produces: [%who '~zod' %where /ford/pages/web %case 60]
549−Wide-form `/$` takes its arguments inside brackets, like `/~`:
550−`/=gas=/$[fuel:html]`
554−`/%` will forward extra arguments (usually from `%eyre`) on to any enclosed `/renderer/`'s. Without this,
555−renderers that use `/$` to read the extra arguments will crash.
559−/= dat /% /tree-json/
563−produces the results of running `ren/tree-json` on the current path. This renderer needs the query string,
564−which is one of the extra arguments passed in from `%eyre`.
566−Wide-form `/%` has no delimiter: `/%/tree-json/`