Fork me on GitHub
#clojure-norway
<
2024-03-21
>
augustl07:03:44

god morgen 🥳

magnars07:03:47

☀️ 👋

teodorlu07:03:08

God morgon! :flag-se: :flag-no:

teodorlu07:03:13

Hvor aktivt bruker dere parprogrammering i hverdagen? Hele tiden? Litt? Ingenting? Skulle dere ønske dere gjorde mer eller mindre parprogrammering?

augustl07:03:48

mer, gjør alt for lite av det

👍 2
teodorlu07:03:43

Er det fordi du ikke er på team hvor det er noen det passer å programmere med? Eller har dere bare for mye å gjøre til å rekke å sette dere ned i ro og mak sammen?

augustl07:03:04

er ikke en del av kulturen hos inneværende kunde

😬 2
augustl07:03:24

nå som vi snakker om det slår det meg at jeg burde gjort en liten innsats her

💪 1
teodorlu07:03:32

det er ikke ansett som effektiv bruk av tid når ikke alle sitter og skriver kode?

slipset08:03:08

Jeg er ikke spesielt glad i parprogrammering, men jeg liker pardesigning.

1
teodorlu08:03:56

så … gjørejobber for seg selv, gå sammen for å ta tyngre beslutninger?

slipset08:03:12

Godt oppsummert

👍 1
slipset08:03:00

Det er litt sånn jeg har oppfattet at @U9MKYDN4Q og @U07FCNURX parprogrammerer?

slipset08:03:45

Skissere noen alternativer sammen, gjerne i kode, og så krønsje ut hver for seg?

cjohansen08:03:53

Ja, til en viss grad. Vi sitter en del sammen, så lenge det er "interessante valg å ta". Litt flytende grense der, men vi deler oss stort sett når det er mest snakk om å banke ut mer av det samme.

👀 1
👍 1
cjohansen08:03:16

Vi skriver nok mer kode sammen enn du antyder @U04V5VAUN 🙂

cjohansen08:03:59

Nå driver vi feks og formulerer en datamodell, det skjemaet skriver vi i sin helhet sammen.

👍 1
teodorlu08:03:13

@U9MKYDN4Q vil du skissere grovt hvor mye dere sitter sammen i forhold til hver for dere? Er ish 50/50, eller er det mer 80/20 i en retning?

slipset08:03:14

Det er vel sånn jeg kanskje hadde gjort sammen med noen på tavla, tegna opp et ER/NIAM diagram og så kanskje implementert selv.

cjohansen08:03:53

Vi skriver Datomic-skjema sammen. Det er en måte å tenke om data på som passer meg godt.

cjohansen08:03:31

@U3X7174KS jeg vil si at det svinger litt etter hvilken fase vi er i. La oss si at det snitter til 50/50, og tidvis er 90/10 i den ene eller andre retningen eller noe sånt? Litt vanskelig å tallfeste.

👍 1
teodorlu08:03:24

skjønner, takk 🙂 Full forståelse for at dette ikke er konstant hver uke. Men da kan man lett si at man “ikke programmerer som dere” hvis man kun sitter sammen torsdag morgen én time hver uke!

cjohansen08:03:49

Nei, det er et stykke fra vår arbeidsflyt 😅

😄 1
👍 1
cjohansen08:03:29

Jeg parprogrammerer mer enn det med @U06P2F094Q0 og han er ikke engang på samme team som meg 😄

😁 1
cjohansen08:03:22

Jeg har hatt så mange parprogrammeringsopplevelser av typen "Dette jeg trodde jeg helt fint kunne stunte sjæl ble bedre når vi satt sammen om det" at jeg lett ser verdien.

👍 1
teodorlu08:03:26

Jeg tror kanskje også det krever et lite “tillitsprang” å lene seg inn i det; at man må gi litt ekstra goodwill den første gangen / de første gangene man prøver. Særlig når én (eller begge) ikke har gjort noe særlig parprogrammering før.

cjohansen08:03:58

Helt klart, det er en ferdighet å mestre som alt mulig annet. Krever trening, tillit og en viss personkjemi.

👍 1
cjohansen08:03:40

Men det finnes ingen bedre måte å sørge for at et team jobber enhetlig

1
teodorlu08:03:47

Selv har jeg egentlig aldri tatt parprogrammering / ensemble-programmering seriøst før i år. Og det innser jeg nå at jeg synes er litt … rart. Men handler vel mye om hvem man får mulighet til å jobbe med tidlig.

cjohansen08:03:10

Ja, det er litt tilfeldig hva man ramler inn i av sånne ting 🙂

boosja09:03:16

I det gamle teamet mitt satt vi sammen 3 stk. ca. 2 timer 3 ganger i uka. Man får noen gode diskusjoner og innsikter i hverandres oppgaver og tanker, men hadde ikke klart å sitte sammen 100% av tiden 😅 Men det er kjempegodt for kompetansedeling og semistore beslutninger

👍 1
boosja09:03:47

Hadde kanskje ønsket å gjøre det mer adhoc, men for å bare komme igang hjelper det med faste tidspunkter 🙂

👍 2
teodorlu09:03:03

Jeg har kjørt en del parprogrammering sammen med to kollegaer i det siste. En ting jeg har måttet lære er å … ta det litt rolig. Ikke prøve å gjøre alt på en gang. Ta tid til diskusjon, ikke bli utålmodig når ting tar litt tid. Og at når vi er 3, er det helt OK at én person går litt til side og gjør andre ting (feks fordi personen trenger en pause), og blir med igjen når det passer.

2
augustl09:03:53

men dette må jo bety at jiraer blir flyttet til høyre halvparten så kjapt? Hvordan ser det ut på burndown charts? trollface

teodorlu09:03:56

Da SMELLER vi bøkene til Marty Cagan i bordet og sier at her på teamet jobber vi for å løse ekte problemer for ekte folk, ikke for å gjøre jobb!

🔥 1
odinodin09:03:22

en god del parprogrammering på prosjektet, funker bra enten for å løse spesielt tunge oppgaver sammen, eller som en del av opplæring av nye på teamet.

👍 1
Jakub Holý (HolyJak)13:03:01

For lite, ønsker mer, med sliter med å prioritere det…

👍 1
boosja07:03:11

Morn morn 😄

pez10:03:50

Morn! Jeg legger mer og mer merke til at jeg mangler en god måte å se JavaScript-objekter i ClojureScript-replen min på.

teodorlu11:03:32

helt fra sidelinja, norsken din er skikkelig god!

💯 1
pez11:03:00

Takk! Det er ikke helt min norsk ännu, utan Nybegynnerspråkeventyrerens 😃 Utom dette svar da, som jeg skrevet helt selv. Haha.

😄 2
pez11:03:43

Som enligt GPTn kunde varit: > Takk! Det er ikke helt min norsk ennå, men Nybegynnerspråkeventyrerens 😃 > Bortsett fra dette svaret da, som jeg har skrevet helt selv. Haha.

😄 2
cjohansen10:03:33

Jeg har laget en proof of concept på "lettvektskomponenter", eller "aliases" (inspirert av Chassis) for Replicant, og tror dette kan bli ganske lekkert. Tanker om denne kodesnutten?

;; I18n stuff

(def dictionaries
  {:nb
   {:title "Min webside"
    :hello "Hei på deg!"
    :click "Klikk knappen"}

   :en
   {:title "My webpage"
    :hello "Hello world!"
    :click "Click the button"}})

(defn lookup-i18n [dictionary _attrs [k]]
  (get dictionary k))

;; A function that adds a bunch of tailwind classes to the markup

(defn button [{:keys [actions spinner? subtle?]} [text]]
  [:button.btn.max-sm:btn-block
   (cond-> (dissoc btn :spinner? :actions :subtle?)
     actions (assoc-in [:on :click] actions)
     subtle? (assoc :class "btn-neutral")
     (not subtle?) (assoc :class "btn-primary"))
   (when spinner?
     [:span.loading.loading-spinner])
   text])

;; Function to turn domain data into hiccup

(defn app [{:keys [locale]}]
  [:div {:replicant/key locale}
   [:h1 [:i18n/k :title]]
   [:p [:i18n/k :hello]]
   [:ui/button {:actions [[:do-stuff]]}
    [:i18n/k :click]]])

;; Render

(defn render-app [state]
  (d/render
   el
   (app state)
   {:aliases {:i18n/k (partial lookup-i18n (dictionaries (:locale state)))
              :ui/button button}}))

;; Render in english
(render-app {:locale :en})

;; ...eller norsk
(render-app {:locale :nb})

💯 2
👀 1
pez10:03:44

Jag vet inte tillräckligt om Replicant för att ha en speciellt värdefull åsikt, men det där ser väldigt trevligt ut!

👍 1
cjohansen10:03:05

Trenger ikke å vite noe om replicant for å ha meninger om hvordan koden leser 😊

pez10:03:33

😃 Jag menar att jag saknar sammanhang och kunskap om alternativ/begränsningar och dylikt.

cjohansen11:03:25

Hehe. Jeg var bare litt nysgjerrig på hva folk tenker om dette. Dette lar deg gjøre transformasjon av data "just in time", altså bare når replicant trenger å oppdatere DOM-en. Tidligere har jeg løst i18n på en tilsvarende måte, men med en walk før rendering. Ved å ha en hook i replicant kan du få det til med mye bedre performance.

🙏 2
cjohansen11:03:04

Jeg har også en hypotese om at dersom man kan uttrykke strukturen i UI-et uten alle renderingdetaljene (som button er et eksempel på), så trenger man ikke domenedata -> uidata -> hiccup. Du kan gå rett fra domenedata til hiccup på denne formen.

larstvei12:03:09

Dette er veldig interessant!

Zeniten13:03:52

Hva er det som gjør dem "lettvekt"?

cjohansen13:03:29

Tja, mulig feil ord? Det er bare mapping av data, ikke noe state eller andre ting man forbinder med komponenter. Så egentlig ikke komponenter i det hele tatt. Men det er effektiv data-transformasjon, siden det kun gjøres idet DOM-en oppdateres - ikke hver gang du "rendrer".

Zeniten13:03:48

Jeg tenkte ikke på ordbruken, egentlig. Det er bare ikke helt klart for meg hva som er nytt her. (Obs: Jeg har ikke brukt Replicant ennå selv, og heller ikke dumdom, dessverre, bare skummet readmeene nå og da.)

larstvei13:03:11

Jeg vet heller ikke om jeg skjønte hvordan dette påvirker performance (men jeg tar deg på ordet assa 😅). Jeg ville anta at den virtuelle DOM-en tar vare på resultatet av (app state), og at det er kun når en node skal rendres at du transformerer med hensyn til :aliases? Gitt at transformasjonene i :aliases genererer mye gørr, så er jo det gørr man slipper å generere for hver rendring. Er jeg inne på noe?

Zeniten13:03:30

Aha, så det var ikke i seg selv noe nytt ved hvordan man lager komponenter? Man skriver f.eks. button som man gjorde før? 🙂

(defn button ...)

Zeniten13:03:12

Det demrer for meg nå, ☀️

cjohansen13:03:11

Det er egentlig bare "late binding" for hiccup-generering

💡 1
msolli14:03:04

Og en slags generalisering av Hiccup? Du binder et keyword til en funksjon med :aliases , og så rendres dette keywordet ved å kalle funksjonen, men bare hvis denne DOM-noden faktisk skal realiseres, altså vises på skjermen. Keywords som ikke fins som alias rendres bare som vanlige DOM-elementer. Noe sånt?

cjohansen14:03:28

Premie til @U06BEJGKD! Litt usikker på hva som er riktig oppførsel for keywords som ikke finnes som alias. Enn så lenge rendrer den en div med barna i og rapporterer en feil i konsollet.

magnars14:03:12

Betyr det at du har enumerert alle gyldige html-tags?

msolli14:03:27

Når du skriver [:p "yo"] - er det riktig å tenke på :p som et alias til en funksjon som lager et p-element i DOM-en?

msolli14:03:41

Jeg liker uansett retningen, og er glad hvis dette betyr at man slipper walk for å låse i18n (slik du gjør i m1p). Du sitter på tallene, kanskje - er det for hastighet først og fremst at du prøver denne veien?

cjohansen14:03:47

@U07FCNURX Nei, det ville jeg unngå. Løsningen ble at aliases må ha namespace.

cjohansen14:03:46

Men i prinsippet kunne jeg slått opp alle tags i alias-definisjonene, men jeg er usikker på om jeg ønsker at det skal være mulig å redefinere :a 😅

cjohansen14:03:15

@U06BEJGKD ref [:p "yo"] ja, men jeg har enn så lenge valgt å ikke støtte det

cjohansen14:03:46

Og ja, å kunne gjøre feks m1p i18n uten walk var hovedmotivasjonen for dette. Kan sikkert brukes til andre cross-cutting ting også.

👌 1
cjohansen14:03:13

Forøvrig kan man også gjøre dette:

[:ui/button#special.btn-primary {:actions [[:do-stuff]]}
 [:i18n/k :click]]
Da får du :id og :class i attributtene til alias-funksjonen 😊

magnars15:03:15

nice 👌 😄

pez20:03:53

TIL: Promise svelger feil hvis man ikke fanger dem med p/catch. Veldig morsomt, må jeg si.