Loading...
+diff --git a/.env.dist b/.env.dist index df10f3e..1b55a44 100644 --- a/.env.dist +++ b/.env.dist @@ -1,2 +1,3 @@ ARCAST_DESKTOP_ADDITIONAL_CHROME_ARGS= -ARCAST_DESKTOP_INSTANCE_ID= \ No newline at end of file +ARCAST_DESKTOP_INSTANCE_ID= +ARCAST_DESKTOP_WEB_APPS=true \ No newline at end of file diff --git a/cmd/mobile/main.go b/cmd/mobile/main.go index ca85e5a..b710b6f 100644 --- a/cmd/mobile/main.go +++ b/cmd/mobile/main.go @@ -77,7 +77,11 @@ func main() { logger.Fatal(ctx, "could not retrieve instance id", logger.CapturedE(errors.WithStack(err))) } - server := server.New(browser, server.WithInstanceID(instanceID)) + server := server.New( + browser, + server.WithInstanceID(instanceID), + server.WithWebApps(true), + ) if err := server.Start(); err != nil { logger.Fatal(ctx, "could not start server", logger.CapturedE(errors.WithStack(err))) diff --git a/go.mod b/go.mod index 267657e..9d18859 100644 --- a/go.mod +++ b/go.mod @@ -4,12 +4,12 @@ go 1.21.4 require ( gioui.org v0.4.1 - git.wow.st/gmp/jni v0.0.0-20210610011705-34026c7e22d0 - github.com/davecgh/go-spew v1.1.1 github.com/gioui-plugins/gio-plugins v0.0.0-20230625001848-8f18aae6c91c - github.com/google/uuid v1.3.0 + github.com/go-chi/cors v1.2.1 github.com/grandcat/zeroconf v1.0.1-0.20230119201135-e4f60f8407b1 + github.com/jaevor/go-nanoid v1.3.0 github.com/pkg/errors v0.9.1 + github.com/wlynxg/anet v0.0.1 github.com/zserge/lorca v0.1.10 ) @@ -17,6 +17,7 @@ require ( cdr.dev/slog v1.6.1 // indirect gioui.org/cpu v0.0.0-20220412190645-f1e9e8c3b1f7 // indirect gioui.org/shader v1.0.8 // indirect + git.wow.st/gmp/jni v0.0.0-20210610011705-34026c7e22d0 // indirect github.com/aymanbagabas/go-osc52/v2 v2.0.1 // indirect github.com/cenkalti/backoff v2.2.1+incompatible // indirect github.com/charmbracelet/lipgloss v0.7.1 // indirect @@ -25,7 +26,6 @@ require ( github.com/go-playground/universal-translator v0.18.0 // indirect github.com/go-text/typesetting v0.0.0-20230803102845-24e03d8b5372 // indirect github.com/inkeliz/go_inkwasm v0.0.0-20220912074516-049d3472c98a // indirect - github.com/jaevor/go-nanoid v1.3.0 // indirect github.com/jchv/go-winloader v0.0.0-20210711035445-715c2860da7e // indirect github.com/jedib0t/go-pretty/v6 v6.4.9 // indirect github.com/leodido/go-urn v1.2.1 // indirect @@ -37,7 +37,6 @@ require ( github.com/muesli/termenv v0.15.2 // indirect github.com/rivo/uniseg v0.4.4 // indirect github.com/russross/blackfriday/v2 v2.1.0 // indirect - github.com/wlynxg/anet v0.0.1 // indirect github.com/xrash/smetrics v0.0.0-20201216005158-039620a65673 // indirect go.opentelemetry.io/otel v1.21.0 // indirect go.opentelemetry.io/otel/trace v1.21.0 // indirect diff --git a/go.sum b/go.sum index aa66902..30be749 100644 --- a/go.sum +++ b/go.sum @@ -34,6 +34,8 @@ github.com/gioui-plugins/gio-plugins v0.0.0-20230625001848-8f18aae6c91c h1:naFDa github.com/gioui-plugins/gio-plugins v0.0.0-20230625001848-8f18aae6c91c/go.mod h1:nBuRsi6udr2x6eorarLHtRkoRaWBICt+WzaE7zQXgYY= github.com/go-chi/chi/v5 v5.0.10 h1:rLz5avzKpjqxrYwXNfmjkrYYXOyLJd37pz53UFHC6vk= github.com/go-chi/chi/v5 v5.0.10/go.mod h1:DslCQbL2OYiznFReuXYUmQ2hGd1aDpCnlMNITLSKoi8= +github.com/go-chi/cors v1.2.1 h1:xEC8UT3Rlp2QuWNEr4Fs/c2EAGVKBwy/1vHx3bppil4= +github.com/go-chi/cors v1.2.1/go.mod h1:sSbTewc+6wYHBBCW7ytsFSn836hqM7JxpglAy2Vzc58= github.com/go-logr/logr v1.3.0 h1:2y3SDp0ZXuc6/cjLSZ+Q3ir+QB9T/iG5yYRXqsagWSY= github.com/go-logr/logr v1.3.0/go.mod h1:9T104GzyrTigFIr8wt5mBrctHMim0Nb2HLGrmQ40KvY= github.com/go-logr/stdr v1.2.2 h1:hSWxHoqTgW2S2qGc0LTAI563KZ5YKYRhT3MFKZMbjag= @@ -50,8 +52,6 @@ github.com/golang/protobuf v1.5.3 h1:KhyjKVUg7Usr/dYsdSqoFveMYd5ko72D+zANwlG1mmg github.com/golang/protobuf v1.5.3/go.mod h1:XVQd3VNwM+JqD3oG2Ue2ip4fOMUkwXdXDdiuN0vRsmY= github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI= github.com/google/go-cmp v0.6.0/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= -github.com/google/uuid v1.3.0 h1:t6JiXgmwXMjEs8VusXIJk2BXHsn+wx8BZdTaoZ5fu7I= -github.com/google/uuid v1.3.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/grandcat/zeroconf v1.0.1-0.20230119201135-e4f60f8407b1 h1:cNb52t5fkWv8ZiicKWnc2eZnhsCCoH7WmRBMIbMp04Q= github.com/grandcat/zeroconf v1.0.1-0.20230119201135-e4f60f8407b1/go.mod h1:I6CSXU4zCGL08JOk9NbcT0ofAgnIkS/fVXbYzfSoDic= github.com/inkeliz/go_inkwasm v0.0.0-20220912074516-049d3472c98a h1:uZklbtdSPrDL/d1EUKd9s8a0Byla2TT01Wg/GZ4xj0w= diff --git a/internal/command/player/run.go b/internal/command/player/run.go index f5c1eae..f24c853 100644 --- a/internal/command/player/run.go +++ b/internal/command/player/run.go @@ -31,6 +31,11 @@ func Run() *cli.Command { EnvVars: []string{"ARCAST_DESKTOP_WINDOW_HEIGHT"}, Value: defaults.Height, }, + &cli.BoolFlag{ + Name: "web-apps", + EnvVars: []string{"ARCAST_DESKTOP_WEB_APPS"}, + Value: false, + }, &cli.IntFlag{ Name: "window-width", EnvVars: []string{"ARCAST_DESKTOP_WINDOW_WIDTH"}, @@ -41,6 +46,7 @@ func Run() *cli.Command { windowHeight := ctx.Int("window-height") windowWidth := ctx.Int("window-width") chromeArgs := addFlagsPrefix(ctx.StringSlice("additional-chrome-arg")...) + webApps := ctx.Bool("web-apps") browser := lorca.NewBrowser( lorca.WithAdditionalChromeArgs(chromeArgs...), @@ -69,7 +75,10 @@ func Run() *cli.Command { instanceID = server.NewRandomInstanceID() } - server := server.New(browser, server.WithInstanceID(instanceID)) + server := server.New(browser, + server.WithInstanceID(instanceID), + server.WithWebApps(webApps), + ) if err := server.Start(); err != nil { return errors.Wrap(err, "could not start server") diff --git a/modd.conf b/modd.conf index 5f59064..8d97c04 100644 --- a/modd.conf +++ b/modd.conf @@ -1,5 +1,6 @@ **/*.go pkg/server/templates/**.gotmpl +pkg/server/apps/** modd.conf .env { prep: make build-client diff --git a/pkg/server/apps.go b/pkg/server/apps.go new file mode 100644 index 0000000..5cbc942 --- /dev/null +++ b/pkg/server/apps.go @@ -0,0 +1,91 @@ +package server + +import ( + "embed" + "encoding/json" + "io/fs" + "net/http" + "os" + "path/filepath" + + "github.com/pkg/errors" + "gitlab.com/wpetit/goweb/api" + + _ "embed" +) + +var ( + apps []App + //go:embed apps/** + appsFS embed.FS +) + +func init() { + if err := initializeAppsList(); err != nil { + panic(errors.WithStack(err)) + } +} + +func initializeAppsList() error { + files, err := fs.Glob(appsFS, "apps/*") + if err != nil { + return errors.WithStack(err) + } + + for _, f := range files { + stat, err := fs.Stat(appsFS, f) + if err != nil { + return errors.WithStack(err) + } + + if !stat.IsDir() { + continue + } + + rawManifest, err := fs.ReadFile(appsFS, filepath.Join(f, "manifest.json")) + if err != nil { + if errors.Is(err, os.ErrNotExist) { + continue + } + + return errors.WithStack(err) + } + + var app App + + if err := json.Unmarshal(rawManifest, &app); err != nil { + return errors.WithStack(err) + } + + app.ID = filepath.Base(f) + + apps = append(apps, app) + } + + return nil +} + +func (s *Server) handleDefaultApp(w http.ResponseWriter, r *http.Request) { + http.Redirect(w, r, "/apps/"+s.defaultWebApp, http.StatusTemporaryRedirect) +} + +type AppsResponse struct { + Apps []App +} + +type App struct { + ID string `json:"id"` + Title map[string]string `json:"title"` + Description map[string]string `json:"description"` + Icon string `json:"icon"` +} + +func (s *Server) handleApps(w http.ResponseWriter, r *http.Request) { + api.DataResponse(w, http.StatusOK, struct { + DefaultApp string `json:"defaultApp"` + Apps []App `json:"apps"` + }{ + DefaultApp: s.defaultWebApp, + Apps: apps, + }) +} diff --git a/pkg/server/apps/home/app.js b/pkg/server/apps/home/app.js new file mode 100644 index 0000000..0cbf315 --- /dev/null +++ b/pkg/server/apps/home/app.js @@ -0,0 +1,19 @@ +fetch('/api/v1/apps') + .then(res => res.json()) + .then(res => { + const defaultApp = res.data.defaultApp + const apps = res.data.apps + + const container = document.createElement("div") + container.className = "container" + apps.forEach(app => { + if (app.id === defaultApp) return + const appLink = document.createElement("a") + appLink.className = "app-link" + appLink.href = "/apps/" + app.id + appLink.innerText = app.title['fr'] + container.appendChild(appLink) + }) + + document.getElementById("main").replaceWith(container); + }) \ No newline at end of file diff --git a/pkg/server/apps/home/index.html b/pkg/server/apps/home/index.html new file mode 100644 index 0000000..c5c8e14 --- /dev/null +++ b/pkg/server/apps/home/index.html @@ -0,0 +1,15 @@ + + +
+ + +Loading...
+Instance ID:
{{ .ID }}
@@ -94,6 +99,15 @@
{{ . }}:{{ $port }}
Apps:
+