Skip to content

Commit

Permalink
Update 04-front-end for magic 8 ball workshop
Browse files Browse the repository at this point in the history
Signed-off-by: Caleb Schoepp <[email protected]>
  • Loading branch information
calebschoepp committed Mar 12, 2024
1 parent c82c2a5 commit 618eee7
Show file tree
Hide file tree
Showing 37 changed files with 2,742 additions and 3,222 deletions.
15 changes: 8 additions & 7 deletions magic-8-ball/04-frontend.md
Original file line number Diff line number Diff line change
@@ -1,25 +1,26 @@
# Magic 8 Ball Frontend

Let's make our Magic 8 Ball application more interactive by adding a frontend where you can submit your question to the omniscient 8 ball! To do this, we want to add a new component to our Spin application that can serve the frontend of our application.
Fortunately, Spin has a [static file server component](https://github.com/fermyon/spin-fileserver) that can be added to any Spin application using `spin add`. Since this will be the base of our application, overwrite the default component trigger with the wildcard `/...` to match all routes.
Fortunately, Spin has a [static file server component](https://github.com/fermyon/spin-fileserver) that can be added to any Spin application using `spin add`. Since this will be the base of our application, we must overwrite the default component trigger with the wildcard `/...` to match all routes.

We also need to tell the fileserver which frontend files to serve. Choose the default `assets` when asked for the 'Directory containing the files to serve'. In your Spin app's directory create a folder named `assets`. For the purposes of this workshop, we've already prepared an HTML, CSS and JS [frontend](apps/frontend/) that you can reuse. Download these files into the `assets` folder.

```bash
$ spin add static-fileserver fileserver
$ spin add fileserver -t static-fileserver
HTTP path: /...
Directory containing the files to serve: assets
```

Let's take a look at the `fileserver` component that has now been added to the application manifest (`spin.toml`). In the component there is a [`files` field](https://developer.fermyon.com/spin/writing-apps#including-files-with-components). Since Wasm has a [capability-based](https://github.com/WebAssembly/WASI/blob/ddfe3d1dda5d1473f37ecebc552ae20ce5fd319a/README.md#capability-based-security) security model, a module can only access files that have been explicitly allowed by the Wasm runtime (wasmtime). This tells Spin to enable the module to read those files at runtime. We set the destination for the files to be the root directory as this is where the [`fileserver`](https://github.com/fermyon/spin-fileserver/blob/main/src/lib.rs#L81) module is configured to look for them.

```toml
[[component]]
source = { url = "https://github.com/fermyon/spin-fileserver/releases/download/v0.0.3/spin_static_fs.wasm", digest = "sha256:38bf971900228222f7f6b2ccee5051f399adca58d71692cdfdea98997965fd0d" }
id = "fileserver"
files = [ { source = "assets", destination = "/" } ]
[component.trigger]
[[trigger.http]]
route = "/..."
component = "fileserver"

[component.fileserver]
source = { url = "https://github.com/fermyon/spin-fileserver/releases/download/v0.2.1/spin_static_fs.wasm", digest = "sha256:5f05b15f0f7cd353d390bc5ebffec7fe25c6a6d7a05b9366c86dcb1a346e9f0f" }
files = [{ source = "assets", destination = "/" }]
```

Let's look at the frontend implementation. The user asks a question and calls our Magic 8 Ball `magic-8` component to get the response. This is done in the `fetch('../magic-8')` call in the JS portion of the snippet below. You can see that we are also passing the question in the body of the request. We will use this in a later step of the workshop. Don't worry about copying the code snippet below. This is just for illustrative purposes.
Expand Down
2 changes: 2 additions & 0 deletions magic-8-ball/apps/03-spin-ai/magic-eight-ball-ts/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ export const handleRequest: HandleRequest = async function (
};

function answer(question: string): string {
console.log(`Question: ${question}`);
const prompt = `<s>[INST] <<SYS>>
You are acting as a Magic 8 Ball that predicts the answer to a questions about events now or in the future.
Your tone should be expressive yet polite.
Expand All @@ -50,5 +51,6 @@ function answer(question: string): string {
if (response.startsWith(answerPrefix)) {
response = response.substring(answerPrefix.length);
}
console.log(`Answer: ${response}`);
return response;
}
Loading

0 comments on commit 618eee7

Please sign in to comment.