Teil 1 - Tooling für die App einrichten
Dieses Lab ist Teil der Amenity Finder Serie, einer umfassenden Anleitung, die Schritt für Schritt zeigt, wie man eine Web-Applikation mithilfe von Web-Components entwickelt. In jedem Teil der Serie werden spezifische Aspekte der Entwicklung behandelt und es werden bewährte Methoden und Techniken vermittelt, um eine moderne und skalierbare Webanwendung aufzubauen.
Im ersten Teil der Amenity Finder Serie widmen wir uns der Einrichtung des Entwicklungsumfelds und der Werkzeuge für unsere Applikation. Wir stellen sicher, dass alle erforderlichen Tools korrekt konfiguriert sind, um die Entwicklung der Web-Components-basierten Applikation zu unterstützen.
Wenn du mit diesem Lab bereits vertraut bist, kannst du im zweiten Teil der Amenity Finder Serie lernen, wie du das Grundlayout für deine Amenity Finder Applikation implementieren kannst.
Vorbereitung
Ziele
In diesem Lab verfolgen wir folgende Ziele:
- Initialisierung eines neuen Projekts mit open-wc: Wir beginnen mit der Initialisierung eines neuen Projekts unter Verwendung des open-wc-Starters. Open-wc ist ein bewährtes Toolkit für die Entwicklung von Web-Components und bietet eine Vielzahl an nützlichen Tools, Konfigurationen und bewährten Methoden. Durch die Initialisierung eines Projekts mit open-wc stellen wir sicher, dass wir eine solide Grundlage haben, um mit Web-Components zu arbeiten.
- Tooling in der
package.json
und in der IDE einrichten: Um das Tooling für unsere Web-Components-Entwicklung einzurichten, bearbeiten wir diepackage.json
-Datei unseres Projekts. Hier können wir verschiedene Skripte hinzufügen, um beispielsweise den Build-Prozess, das Testen oder das Starten der Entwicklungsserver zu automatisieren. Darüber hinaus können wir zusätzliche Abhängigkeiten hinzufügen, die uns bei der Entwicklung unterstützen. Zusätzlich richten wir unsere IDE oder unseren Texteditor ein, um von hilfreichen Plugins wie Prettier, ESLint oder lit-plugin zu profitieren. Diese Tools unterstützen uns bei der Codeformatierung, Fehlererkennung und bieten eine bessere Entwicklungsumgebung für Web-Components. - Deploy der neuen App über surge.sh in die Cloud (optional): Als optionales Ziel können wir unsere fertige Web-Components-App in die Cloud deployen, um sie für andere zugänglich zu machen. Eine beliebte Plattform für das Deployment von statischen Websites ist surge.sh. Surge.sh ermöglicht es uns, unsere Anwendung mit nur wenigen einfachen Schritten zu deployen und sie unter einer öffentlichen URL verfügbar zu machen. Dies bietet die Möglichkeit, die Anwendung mit anderen zu teilen oder sie auf verschiedenen Geräten zu testen.
Schritte
Das Setup der Amenity Finder Applikation umfasst sechs Schritte, wobei die letzten drei optional sind und nicht zwingend durchgeführt werden müssen.
- Projekt initialisieren
- Applikation starten
- Git-Repository Aufsetzen
- Husky Aufsetzen (optional)
- IDE Setup (optional)
- Cloud Deployment (optional)
Branch
Der erste Teil des Amenity Finder Labs ist auf GitHub verfügbar.
Wichtige Links
Für weiterführende Informationen zu den behandelten Themen empfehlen wir dir, die folgenden Links zu besuchen:
Los geht’s!
Projekt initialisieren
Wir initialisieren unser Projekt mithilfe von Open Web Component Recommendations (open-wc). open-wc ist eine Sammlung von Empfehlungen und Einstellungen für Projekte auf Basis von Web-Components. Die Empfehlungen decken viele Bereiche wie Entwicklung, Linting, Testing, Publishing usw. ab.
open-wc bietet auch einen npm initializer für das Aufsetzen von neuen Projekten an. Wir setzen unsere Applikation mit diesem Generator auf, indem wir den folgenden Befehl ausführen:
$ npx @open-wc/create@0.38.70
(Eigentlich wäre der Befehl noch kürzer, nämlich npm init @open-wc
. Allerdings möchten wir sicherstellen, dass wir mit den möglichst gleichen Versionen arbeiten. Um bei einem npm initializer Package die Version angeben zu können, müssen wir den darunterliegenden Befehl npx
verwenden.)
Als Erstes sollten wir den folgenden Output sehen:
_.,,,,,,,,,._
.d'' ``b. Open Web Components Recommendations
.p' Open `q.
.d' Web Components `b. Start or upgrade your web component project with
.d' `b. ease. All our recommendations at your fingertips.
:: ................. ::
`p. .q'
`p. open-wc.org .q'
`b. @openWc .d'
`q.. ..,' See more details at https://open-wc.org/init/
'',,,,,,,,,,''
Note: you can exit any time with Ctrl+C or Esc
? What would you like to do today? › - Use arrow-keys. Return to submit.
❯ Scaffold a new project
Da wir eine neue App aufsetzen, wählen wir hier die Option Scaffold a new project
.
Der Generator führt uns nun durch mehrere Fragen. Diese beantworten wir wie folgt:
tl;dr
Die voreiligen Leser finden nachfolgend eine Zusammenfassung der Antworten für den @open-wc
Generator. Eine detaillierte Beschreibung folgt weiter unten.
✔ What would you like to do today? › Scaffold a new project
✔ What would you like to scaffold? › Application
✔ What would you like to add? › Linting (eslint & prettier), Building (rollup)
✔ Would you like to use typescript? › No
✔ Would you like to scaffold examples files for? › Building (rollup)
✔ What is the tag name of your app shell element? … amenity-finder
✔ Do you want to write this file structure to disk? › Yes
✔ Do you want to install dependencies? › Yes, with npm
Erklärungen zu den Fragen und Antworten
What would you like to scaffold?
- Wir wählen
Application
, da wir eine Applikation und keine eigenständige Webkomponente bauen.
- Wir wählen
What would you like to add?
- Hier beschränken wir uns auf die Optionen
Linting (eslint & prettier)
undBuilding (rollup)
. - Linting liefert uns unter anderem Konfigurationen für Code-Linting mittels ESLint sowie eine automatische Code-Formatierung mithilfe von Prettier. ESLint gehört heute zum Quasi-Standard für statische Analysen von JavaScript (oder auch TypeScript) Programmcode. Prettier ist ein «opinionated code formatter», der mit vielen verschiedenen Sprachen umgehen kann. Wir müssen uns so keine Sorgen um eine konsistente Formatierung machen. Beide Tools haben ein umfangreiches Ökosystem und können mittels Plugins für verschiedene Anwendungsfälle erweitert werden.
- Bei der Entwicklung werden wir dank @web/dev-server ohne einen Build (buildless) unterwegs sein. Für ein optimiertes Produktions-Bundle verwendet open-wc Rollup.
Demoing (storybook)
lassen wir für unseren Anwendungsfall ganz weg. Wer sich trotzdem für den Anwendungsfall von Storybook für die Dokumentation (und Testing) von Web-Components interessiert, kann dies im Demoing-Abschnitt auf der open-wc Webseite nachlesen.- Den Punkt
Testing (karma)
lassen wir zum jetzigen Zeitpunkt ebenfalls noch aus. Wir kommen später in einem separaten Kapitel zum Thema Testing noch einmal darauf zurück. Building (rollup)
wird für das Builden eines Bundles für die Produktion verwendet.
- Hier beschränken wir uns auf die Optionen
Would you like to use typescript?
- Um möglichst nah bei der Web-Plattform zu bleiben, werden wir unsere Applikation in JavaScript schreiben und wählen daher
No
.
- Um möglichst nah bei der Web-Plattform zu bleiben, werden wir unsere Applikation in JavaScript schreiben und wählen daher
What is the tag name of your application/web component?
- Wir bauen einen Restaurant-Finder und wählen für den Custom-Tag daher die englische Übersetzung
amenity-finder
. Über den<amenity-finder>
-Tag wird unsere Applikation später im HTML-Dokument eingebunden.
- Wir bauen einen Restaurant-Finder und wählen für den Custom-Tag daher die englische Übersetzung
Do you want to write this file structure to disk?
- Zum Schluss bestätigen wir noch das Schreiben der gesamten Projektverzeichnisstruktur mit
Yes
.
- Zum Schluss bestätigen wir noch das Schreiben der gesamten Projektverzeichnisstruktur mit
Do you want to install dependencies?
- Optional kann der open-wc Generator für uns auch noch alle npm-Dependencies im Zielordner installieren. Dies können wir entweder mit Yarn oder npm machen. Über die Vor- und Nachteile der beiden Tools herrscht auch im 2021 Uneinigkeit. Weil npm als Teil der Node-Installation mitgeliefert wird, holen wir unsere Dependencies damit und wählen hier
Yes, with npm
.
- Optional kann der open-wc Generator für uns auch noch alle npm-Dependencies im Zielordner installieren. Dies können wir entweder mit Yarn oder npm machen. Über die Vor- und Nachteile der beiden Tools herrscht auch im 2021 Uneinigkeit. Weil npm als Teil der Node-Installation mitgeliefert wird, holen wir unsere Dependencies damit und wählen hier
Applikation starten
Das Resultat des open-wc Generators sollte ein Verzeichnis amenity-finder
mit der folgenden Verzeichnisstruktur sein. Wir werden auf diese Struktur in der nächsten Lektion näher eingehen.
amenity-finder/
├── assets/
│ └── open-wc-logo.svg
├── src/
│ ├── amenity-finder.js
│ └── AmenityFinder.js
├── .editorconfig
├── .gitignore
├── custom-elements.json
├── index.html
├── LICENSE
├── package.json
├── package-lock.json
├── README.md
├── rollup.config.js
└── web-dev-server.config.mjs
Wir wechseln mit $ cd amenity-finder
in das Applikationsverzeichnis1 und können mit $ npm start
die Applikation starten. Falls ihr vorher die Frage Do you want to install dependencies?
mit No
beantwortet habt, muss vorher noch $ npm install
ausgeführt werden, um die npm-Dependencies zu installieren.
Das Start-Skript sollte die URL http://localhost:8000/ automatisch im Browser öffnen. Et voilà! Unsere Applikation startet und du solltest den folgenden Screen sehen:
Git-Repository Aufsetzen
Damit wir unseren Entwicklungsfortschritt tracken und unsere Anpassungen versionieren können, setzen wir noch ein lokales Git-Repository auf.
$ git init
$ git add -A .
$ git commit -am 'Initial import'
Husky aufsetzen (optional)
Das open-wc-Setup verwendet Husky für die Installation von Git Hooks. So wird bei jedem Commit zum Beispiel der $ npm run lint
Befehl gestartet. Damit kann verhindert werden, dass falsch formatierter Code oder Code der die statische Analyse mit ESLint nicht ohne Fehler durchläuft, in das Repository committed werden kann.
Husky installiert die Git Hooks automatisch bei npm install
in das .git
Verzeichnis. Haben wir allerdings beim initialen Setup die Frage Do you want to install dependencies?
mit Yes
beantwortet, sind die Hooks nicht installiert worden, weil wir uns zum Zeitpunkt von npm install
ausserhalb des Projekt-Roots befunden haben. Mit npm rebuild
können wir die Hooks nachträglich installieren lassen.
Ihr könnt nun selber einfach testen, ob bei jedem Commit Husky die lint-Befehle ausführt.
IDE Setup (optional)
Wir beschränken uns in dieser Lektion auf das Setup von IntelliJ IDEA resp. den anderen JetBrains IDE-Varianten wie WebStorm oder PhpStorm. Anleitung für weitere Entwicklungsumgebungen wie z. B. Visual Studio Code, Atom oder Sublime Text sind auf der open-wc Webseite zu finden.
Die aktuelle Version 2021.x von IntelliJ IDEA Ultimate unterstützt ESLint und Prettier von Haus aus. In anderen JetBrains IDE-Varianten müssen womöglich folgende Plugins installiert werden:
ESLint und Prettier werden am besten wie folgt konfiguriert:
Cloud Deployment (optional)
Wir wollen unsere Applikation anderen zur Verfügung stellen. Dafür muss sie auf einem Webserver öffentlich zugänglich sein. Weil sie aus rein statischen Files (HTML und JavaScript) besteht, brauchen wir dafür nur ein einfaches statisches Hosting. Heute gibt es zahlreiche Anbieter für diesen Anwendungsfall. Wir werden in unserem Beispiel Surge verwenden. Weitere beliebte Alternativen sind Github Pages, Netlify, Heroku, Vercel oder Google Firebase.
Mit npm start
hatten wir bisher nur einen Development-Server gestartet. Beim initialen Setup hatten wir allerdings auch einen Build, den wir für ein produktives Deployment verwenden können, aufgesetzt (respektive hat dies npm init @open-wc
für uns getan). Den Build können wir mit dem folgenden Befehl starten …
$ npm run build
… und erhalten den folgenden Output:
> amenity-finder@0.0.0 build
> rimraf dist && rollup -c rollup.config.js && npm run analyze -- --exclude dist
index.html → dist...
The service worker file was written to dist/sw.js
The service worker will precache 2 URLs, totaling 18 kB.
created dist in 2.5s
> amenity-finder@0.0.0 analyze
> cem analyze --litelement "--exclude" "dist"
[5:35:19 PM] @custom-elements-manifest/analyzer: Created new manifest.
Der Build unserer Applikation landet also im dist
Verzeichnis. Mit einem einfachen Webserver können wir den Inhalt dieses Verzeichnis über unseren localhost
auf einem Port ausliefern und so einfach eine Webserver-Umgebung simulieren:
$ npx http-server dist
Standardmässig wird ein Server auf dem Port 8080
gestartet. Ist dieser besetzt, wird beim Port einfach hochgezählt bis ein freier Port gefunden wurde. Unter http://127.0.0.1:8080/ sollten wir also den Build unserer Applikation sehen.
Nun müssen wir noch Surge installieren um dann über den surge
Kommandozeile-Befehl das Deployment in die Cloud machen zu können:
$ npm install surge --global
Das Deployment erledigen wir dann über den Befehl:
$ surge dist
Haben wir noch kein Benutzerkonto bei Surge, können wir im gleichen Zug einen erstellen. Bestehende Benutzer können mit dem Surge-Benutzerkonto einloggen. Surge erstellt für uns eine zufällige Subdomain auf surge.sh
und lädt den Inhalt unseres dist
Verzeichnisses hoch. Ein Beispiel-Output des vorherigen Befehls könnte so aussehen:
Welcome to surge! (surge.sh)
Login (or create surge account) by entering email & password.
email: psiska@inventage.com
password:
Running as psiska@inventage.com (Student)
project: dist
domain: itchy-frog.surge.sh
upload: [====================] 100% eta: 0.0s (7 files, 176809 bytes)
CDN: [====================] 100%
encryption: *.surge.sh, surge.sh (229 days)
IP: 138.197.235.123
Success! - Published to itchy-frog.surge.sh
Unsere Applikation ist nun unter http://itchy-frog.surge.sh/ aufrufbar. Ohne weitere Konfiguration erstellt Surge bei jedem Deployment eine solche zufällige Domain. Damit unsere Applikation immer unter der gleichen Domain erreichbar ist, können wir das Surge entweder über den --domain
Parameter mitgeben, oder wir legen eine Datei CNAME
mit der Domain als Inhalt an.
In unserem Fall ist der --domain
Parameter der einfachere Weg (weil der Inhalt von dist
durch Rollup generiert wird und wir so vorerst nichts an der Rollup-Konfiguration rollup.config.js
anpassen müssen). Damit wir uns die Befehle und Parameter nicht merken müssen, erstellen wir uns dafür ein npm-Skript im package.json
.
--- package.json
+++ package.json
"build": "rimraf dist && rollup -c rollup.config.js && npm run analyze -- --exclude dist",
"start:build": "web-dev-server --root-dir dist --app-index index.html --open",
"analyze": "cem analyze --litelement",
- "start": "web-dev-server"
+ "start": "web-dev-server",
+ "deploy": "surge --domain itchy-frog.surge.sh dist"
},
"dependencies": {
"lit": "^2.0.0-rc.4"
Danach können wir unsere Applikation mit $ npm run deploy
mit Surge deployen.
ACHTUNG: Der $ npm run deploy
Befehl ist nur für das Deployment des Inhalts des dist
Verzeichnis zuständig. Vor jedem Deployment müssen wir npm run build
ausführen, um einen aktuellen Build der Applikation zu erhalten. Möchte man dies nicht, kann das deploy
Skript entsprechend noch um einen Aufruf des build
Skripts ergänzt werden:
--- package.json
+++ package.json
"start:build": "web-dev-server --root-dir dist --app-index index.html --open",
"analyze": "cem analyze --litelement",
"start": "web-dev-server",
- "deploy": "surge --domain itchy-frog.surge.sh dist"
+ "deploy": "npm run build && surge --domain itchy-frog.surge.sh dist"
},
"dependencies": {
"lit": "^2.0.0-rc.4"
Glückwunsch!
Du hast den ersten Teil der Amenity Finder Serie abgeschlossen. In diesem Teil haben wir das Tooling für die App aufgesetzt. Du hast eine aktuelle Node.js Installation eingerichtet und eine geeignete IDE oder Editor ausgewählt. Dadurch bist du bereit, mit der Entwicklung der Amenity Finder Applikation zu beginnen. Im zweiten Teil werden wir das Basis-Layout für die App implementieren.
Footnotes
1 Wir führen von hier an alle Befehle jeweils im amenity-finder
Verzeichnis aus. ↩