WebST: Framework & Tools for Test-Driven Development of Web Components with Smalltalk

nourybouraqadi 129 views 60 slides Jul 11, 2024
Slide 1
Slide 1 of 60
Slide 1
1
Slide 2
2
Slide 3
3
Slide 4
4
Slide 5
5
Slide 6
6
Slide 7
7
Slide 8
8
Slide 9
9
Slide 10
10
Slide 11
11
Slide 12
12
Slide 13
13
Slide 14
14
Slide 15
15
Slide 16
16
Slide 17
17
Slide 18
18
Slide 19
19
Slide 20
20
Slide 21
21
Slide 22
22
Slide 23
23
Slide 24
24
Slide 25
25
Slide 26
26
Slide 27
27
Slide 28
28
Slide 29
29
Slide 30
30
Slide 31
31
Slide 32
32
Slide 33
33
Slide 34
34
Slide 35
35
Slide 36
36
Slide 37
37
Slide 38
38
Slide 39
39
Slide 40
40
Slide 41
41
Slide 42
42
Slide 43
43
Slide 44
44
Slide 45
45
Slide 46
46
Slide 47
47
Slide 48
48
Slide 49
49
Slide 50
50
Slide 51
51
Slide 52
52
Slide 53
53
Slide 54
54
Slide 55
55
Slide 56
56
Slide 57
57
Slide 58
58
Slide 59
59
Slide 60
60

About This Presentation

Web Components are standard web technologies that support the definition of reusable custom HTML elements. This talk introduces WebST (https://github.com/bouraqadi/WebST) a solution to seamlessly implement and test web components using the powerful Pharo Smalltalk IDE (https://pharo.org). By delvin...


Slide Content

1
WebST
30th ESUG Conference
European Smalltalk Users Group
Lille, France, 8 - 11 July 2024

2
I want to
make this
web page

3
Updates
every
second

4
Different
View States

5
But, I am
Lazy!

6Web Components
you reuse must
\

7
Noury
Bouraqadi

8PLC3000.com
Noury
Bouraqadi

9
Web Components
&
Smalltalk

●Custom HTML tags
●HTML + CSS + JS
●Encapsulation = No collisions
10
Web Components = W3C Standard
webcomponents.org

11
<countdown-timer date="2024-07-08T09:00:00"
heading="ESUG 2024" …></countdown-timer>
<countdown-timer date="2024-10-18T18:00:00"
heading="Smalltalk ...></countdown-timer>
<script src="./countdown-timer.min.js"></script>

12
But, what if
I have special
requirements?

13
In Smalltalk
Web
Components
you make!

14
A Component Example
<ws-counter></ws-counter>

15
Web Browsers Build Objects from HTML
HtmlElement

html
body
head
……
Children

16
Web Browsers Build Objects from HTML
HtmlElement

html
body
head
……
Children
The DOM
(Document Object
Model)

17
Adding a Component = Adding a Subclass
<ws-counter></ws-counter>
HtmlElement

html
body
head
ws-counter
…… …

18
Component = View + Model
WsCounterComponent
WsCounterModel WsCounterView

Component View = HTML + CSS ?
19
WsCounterView
WsCounterComponent
WsCounterModel

Component View = HTML + CSS ?
20
WsCounterView
WsCounterComponent
WsCounterModel
Not
Smalltalk!

21

The
force
you must use

22

The
force
you must use
Thanks to Master Johan Brichau
& to the other Jedis!

23
●Client: HTML Generation
●Server: Requests Handling
Web Apps in Smalltalk

24
Counter View Required HTML
<div class="display me-1 text-center fs-1">42</div>
<button class="increment btn btn-primary" type="button">+</button>
<button class="decrement btn btn-info" type="button">-</button>
<button class="reset btn btn-danger" type="button">x</button>

25
Counter View Definition
renderOuterHtmlOn: html
html div class: 'display me-1 text-center fs-1'.
html button class: 'increment btn btn-primary'; value: '+'.
html button class: 'decrement btn btn-info'; value: '-'.
html button class: 'reset btn btn-danger'; value: 'x'

26
Component Model = Business as Usual |
WsCounterComponent
WsCounterModel WsCounterView

27
Component Model
increment
self count: self count + 1.
count
^count
count: newCount
count := newCount.
countPort notifyWith: newCount
Trivial
|

28
Model = Subject in the Observer Design Pattern
increment
self count: self count + 1.
count
^count
count: newCount
count := newCount.
countPort notifyWith: newCount
Announcer

29
Component Links View & Model = MVC
WsCounterComponent
WsCounterModel WsCounterView

initModel
super initModel.
model -@ #countPort => [ :newCount |
self displayCount: newCount ].
self updateDisplay
updateDisplay
display textContent: model count asString
30
Component Links Model to View
Update View When
Model Changes

initModel
super initModel.
model -@ #countPort => [ :newCount |
self displayCount: newCount ].
self updateDisplay
updateDisplay
display textContent: model count asString
31
View Observes the Model
Subscribe to count changes

initView
| incrementButton decrementButton resetButton |
super initView.
display := view querySelector: '.display'.
incrementButton := view querySelector: '.increment'.
self onClickElement: incrementButton do: [ model increment ].
decrementButton := …
32
Component Links View to Model
Clicks on View
Increment Model

initView
| incrementButton decrementButton resetButton |
super initView.
display := view querySelector: '.display'.
incrementButton := view querySelector: '.increment'.
self onClickElement: incrementButton do: [ model increment ].
decrementButton := …
33
Navigating the DOM
JavaScript
API !
?

12
34
❤The
force
you must use
Develop
100% Pharo
Run 100%
JavaScript

35●Generate JavaScript from Smalltalk
●Link JavaScript Third Party Libraries
●Test JavaScript + Web Clients
Develop 100% Pharo
Run 100% JavaScript

36
HTML
JavaScript
Smalltalk

37
HTML ✅
JavaScript ✅
CSS❓

38HTML ✅
JavaScript ✅
CSS❓
Reuse
you must!
The JavaScript
force you must use!

39
Reuse
Candidate

A View can Link Resources
40
WsCounterView
WsCounterComponent
WsCounterModel
Bootstrap
CSS
Bootstrap
JS

41
to Render CSS Resources
renderTagOn: html
^ html link
beStylesheet;
url: self url;
yourself

42
to Render JavaScript Resources
renderTagOn: html
^ html script
defer;
type: 'text/javascript';
url: self url;
yourself

43
HTML
JavaScript
Smalltalk CSS

44
Smalltalk
Web
Components
Framework
+ Tools

45
Smalltalk
Web
Components
WebST

46
Smalltalk
WebST
Standalone
Web
Clients
JSHTML

47How to Make
Complex
Components?
21
Player B
18
Player A
Game Score

48How to make
complex
components?
21
Player B
18
Player A
Game Score
Composite Design
Pattern
You must use!

49
21
Player B
18
Player A
Game Score
Editable Text
Component
Counter
Component

50
View Rendering Sub-Components
Score
Component
Score
View
Counter
Component
Editable Text
Component

51
html
render: EditableTextComponent
dataAttributes: { #text -> 'Game Score' }.
View Rendering Sub-Components
<ws-editable-text data-text="Game Score">
</ws-editable-text>
Generated HTML
Smalltalk

52I want
more!
I want to develop
100% in Smalltalk
ALL THE TIME!

53

Export Full Web
Clients + Server
You Can

54
Wait!
I want
Test-Driven Development
too!

55

The
TDD force
you must use
Test Client-Server
Interaction from
Both Sides!

100%
Pharo
HTML + JavaScript
DevelopmentProduction
1. Write tests
3. Export
2. Pass the tests
56
Server + Clients 100%

57
WebST
Final Thoughts
Development Production

58
WebST

59
Willow Code
Paradise
Egg
Smalltalk
WebST

60
WebST
Web Components
& Smalltalk
.com/bouraqadi/WebST