All Projects → y-taka-23 → miso-tutorial-app

y-taka-23 / miso-tutorial-app

Licence: BSD-3-Clause license
An example GHCJS + Miso single page application. 🍜

Programming Languages

haskell
3896 projects
shell
77523 projects

Projects that are alternatives of or similar to miso-tutorial-app

Koa Vue Notes Web
🤓 This is a simple SPA built using Koa as the backend, Vue as the first frontend, and React as the second frontend. Features MySQL integration, user authentication, CRUD note actions, and Vuex store modules.
Stars: ✭ 200 (+344.44%)
Mutual labels:  spa
The Elmish Book
A practical guide to building modern and reliable web applications in F# from first principles
Stars: ✭ 231 (+413.33%)
Mutual labels:  spa
Vuetober
A webpack starting point for single page apps with October CMS and Vue
Stars: ✭ 251 (+457.78%)
Mutual labels:  spa
Auth0 Vue Samples
Auth0 Integration Samples for Vue.js Applications
Stars: ✭ 215 (+377.78%)
Mutual labels:  spa
Auth0 Angular Samples
Auth0 Integration Samples for Angular 2+ Applications
Stars: ✭ 227 (+404.44%)
Mutual labels:  spa
Blog Admin
blog-admin @react、@typescript、@apollographql
Stars: ✭ 239 (+431.11%)
Mutual labels:  spa
Rustmart Yew Example
Single Page Application (SPA) written using Rust, Wasm and Yew
Stars: ✭ 196 (+335.56%)
Mutual labels:  spa
vue-auth-boilerplate
This is a simple Vue template/starter kit, scaffolded on vue-cli 3, with full Auth functions to Login & Register
Stars: ✭ 77 (+71.11%)
Mutual labels:  spa
Mmf Blog Vue2
mmf-blog vue2.0 (vue2, vue-router, vuex)
Stars: ✭ 232 (+415.56%)
Mutual labels:  spa
Prism
Build frontend web apps with Ruby and WebAssembly
Stars: ✭ 251 (+457.78%)
Mutual labels:  spa
Cloudtunes
Web-based music player for the cloud ☁️ 🎶 Play music from YouTube, Dropbox, etc.
Stars: ✭ 2,449 (+5342.22%)
Mutual labels:  spa
Notadd
A microservice development architecture based on nest.js. —— 基于 Nest.js 的微服务开发架构。
Stars: ✭ 2,556 (+5580%)
Mutual labels:  spa
Butterfly Server
The Everything is Real-Time C# Backend for Single Page Applications
Stars: ✭ 247 (+448.89%)
Mutual labels:  spa
Webhook.site
⚓️ Easily test HTTP webhooks with this handy tool that displays requests instantly.
Stars: ✭ 2,842 (+6215.56%)
Mutual labels:  spa
Laravel Vue Spa
A Laravel-Vue SPA starter kit.
Stars: ✭ 2,889 (+6320%)
Mutual labels:  spa
Maka
Maka.js是基于react的一个前端微服务开发框架(makajs.com)
Stars: ✭ 200 (+344.44%)
Mutual labels:  spa
Productivity Frontend
Productivity Application - Kanban Style Productivity Management Application with Customizable Boards, Lists and Cards to Make You More Productive.
Stars: ✭ 234 (+420%)
Mutual labels:  spa
laravel-vue-spa-boilerplate
Laravel Vue Spa BoilerPlate
Stars: ✭ 36 (-20%)
Mutual labels:  spa
react-redux-boilerplate
A React boilerplate based on Redux, React Router, styled components and Parcel
Stars: ✭ 62 (+37.78%)
Mutual labels:  spa
Terraform Aws Cognito Auth
Serverless Authentication as a Service (AaaS) provider built on top of AWS Cognito
Stars: ✭ 248 (+451.11%)
Mutual labels:  spa

Example SPA in Miso

Docker Automated build Docker Build Status

An example GHCJS + Miso single page application.

screenshot

Running the Application

Docker

The application is packed as a Docker image, so you can launch it with a single command.

docker run -d -p 4000:4000 ytaka23/miso-tutorial-app:latest

Access http://localhost:4000.

Source

You can also build the application from source code. Note that, if it's your first experience of GHCJS, it takes a long time to set up the compiler.

git clone https://github.com/y-taka-23/miso-tutorial-app.git
cd miso-tutorial-app
./run.sh

The script prepares compilation environments according to each stack.yaml, builds both of the client/server side stuffs and starts the web server. Access http://localhost:4000.

Highlights

This project is ported from Elm implementation. Miso framework aims to provide "The Elm Architecture" for GHCJS, thus its architecture looks very close to the original Elm application. Nevertheless, the Miso implementation has several interesting differences.

Isomorphism

Isomorphism, also known as server side rendering (SSR,) is one of the most remarkable features of Miso framework. Implementing both of the client and server sides in the same language, that is Haskell, Miso can reuse most of the application and optimize the cost of renering.

As with The Elm Architecture, an isomorphic Miso application consists of the following parts:

  • Model stores states of the application.
  • Action triggers a state transition with a payload (Msg in Elm.)
  • Update makes a transit from the current state to the next, according to the incoming action.
  • Subscription catches mainly user's input.
  • Effect outputs anything to the outside world (Cmd in Elm.)
  • View converts the model to an HTML response.
  • Routing determines which page should be rendered.

In Miso isomorphism, the models, actions and views are "shared" between the client/server sides. When a browser accesses the web server for the first time, the server returns an HTML file built from the initial model and the view logic. Next, when the user changes the current URL (by a subscription) or accesses external APIs (by an effect,) JavaScript re-renders the page by the shared view and routing logic in the client side only.

Client Shared Server
Update Model (Servant Server)
Subscription Action
Effect View
Routing

Path-based Routing by Servant API

On the top of Haskell's powerful type system, Miso can denote its routing as types, in the similar way with Servant. The following defines three routes : /, /players and /players/:id as a single page application.

type Route =
         TopRoute
    :<|> ListRoute
    :<|> EditRoute

type TopRoute = View Action

type ListRoute = "players" :> View Action

type EditRoute = "players" :> Capture "ident" PlayerId :> View Action

Besides, for the server side, Miso converts and extends the client side routes to define the APIs. In the following snippet there are four APIs:

  • JsonApi returns JSON files for XHR by Miso effects; /api/players and /api/players/:id.
  • IsomorphicApireturns HTML files generated by SSR.
  • StaticApi returns static resources including JavaScript.
  • NotFoundApi returns the 404 error page.
type Api = JsonApi :<|> IsomorphicApi :<|> StaticApi :<|> NotFoundApi

type JsonApi =
         "api" :> "players" :> Get '[JSON] [Player]
    :<|> "api" :> "players" :> Capture "id" PlayerId
            :> ReqBody '[JSON] Player :> Put '[JSON] NoContent

type IsomorphicApi = ToServerRoutes Route HtmlPage Action

type StaticApi = "static" :> Raw

type NotFoundApi = Raw

Effects in IO Monads

In The Elm Architecture, the update function has a type:

update : Msg -> Model -> (Model, Cmd Msg)

On the other hand in Miso:

updateModel :: Action -> Model -> Effect Action Model

The Effect type is a sort of aliases, to handle IO actions asynchronously, implemented as:

data Effect action model = Effect model [Sub action]
type Sub action = Sink action -> IO ()
type Sink action = action -> IO ()

It means that Miso can do arbitrary IO actions as effects. Moreover it provides several constructors to simply denote update with/without effects:

(<#) :: model -> IO action -> Effect action model
noEff :: model -> Effect action model

Let's back to the example. Here fetchPlayers is just an IO action to fetch a player list via external connection. updateModel passes the result to SetPlayers, then again updateModel sets the player list without effects.

fetchPlayers :: IO (Either String [Player])
updatePlayer :: Either String Player -> Model -> Model

updateModel FetchPlayers m = m <# do
    SetPlayers <$> fetchPlayers
updateModel (SetPlayer eP) m = noEff $ updatePlayer eP m

For more detail, see the implementation.

References

Note that the project description data, including the texts, logos, images, and/or trademarks, for each open source project belongs to its rightful owner. If you wish to add or remove any projects, please contact us at [email protected].