Differenz Zeitstempel Arbeitszeit

Gast #7354559
Lesenswert?

Hallo.

Ich habe zwei Zeitstempel und möchte die Differenz dazwischen berechnen ABER nur während der Arbeitszeit von 9 bis 17 Uhr. Es kann auch sein dass die Zeitstempel nicht in der Arbeitszeit erstellt wurden. Normalerweise wurde ich einfach die beiden Zeitstempel in Sekunden wandeln und dann ein diff machen. Gibt es einen eleganten Weg nur die Zeit zwischen 9 und 17 Uhr in der Woche zu zählen? zB Date1 20.02.2023 6:35 Date2 21.02.2023 10:04

sollte 8h + 1:04h = 9:04h ergeben.

Das Ganze sollte als Shell Script unter Linux laufen. Kein Excel.

Martin

#7354618
Lesenswert?

"dateutils" installiert, oder kannst du die nachinstallieren? "apt install dateutils"?

1
DATE1="20.02.2023 6:35"
2
DATE2="21.02.2023 10:04"
3

4
TS1=$(/usr/bin/dateutils.strptime -i '%d.%m.%Y %H:%M' "$DATE1" -f '%s')
5
TS2=$(/usr/bin/dateutils.strptime -i '%d.%m.%Y %H:%M' "$DATE2" -f '%s')
6

7
echo "$(($TS2-$TS1)) Sekunden liegen zwischen '$DATE1' und '$DATE2'"

Danach fängt der schwierige Teil an. Schleife über ganze Tage (Tag=$(date -d "$Tag + 1 day") oder so), für jeden Tag die Timestamps Arbeitszeit-Begin/Ende berechnen, in großer If-then-else-Orgie mit den TS1/2 vergleichen, nur die darinnenliegenden Intervalle (Sekunden) aufsummieren.

ganz zum Schluss die Sekunden wieder in ein Freudliches Tage/Stunden/Minuten Format zurückrechnen.

Alles in allem: In der Bash durchaus machbar.

#7354639
Lesenswert?

In etwa so:

1
DATE1="20.02.2023 06:35"
2
DATE2="21.02.2023 10:04"
3

4
TS1=$(/usr/bin/dateutils.strptime -i '%d.%m.%Y %H:%M' "$DATE1" -f '%s')
5
TS2=$(/usr/bin/dateutils.strptime -i '%d.%m.%Y %H:%M' "$DATE2" -f '%s')
6

7
echo "$(($TS2-$TS1)) Sekunden liegen zwischen '$DATE1' und '$DATE2'"
8

9
STARTTAG=$(/usr/bin/dateutils.strptime -i '%d.%m.%Y %H:%M' "$DATE1" -f '%Y-%m-%d')
10
ENDTAG=$(/usr/bin/dateutils.strptime -i '%d.%m.%Y %H:%M' "$DATE2" -f '%Y-%m-%d')
11

12
TOTAL=0
13
while [ \! $STARTTAG \> $ENDTAG ]; do
14
  echo -n " - prüfe Tag $STARTTAG: "
15
  AZBEGIN=$(date -d "$STARTTAG 09:00" +"%s")
16
  AZENDE=$(date -d "$STARTTAG 17:00" +"%s")
17

18
  if [ $AZBEGIN -lt $TS1 ]; then
19
    AZBEGIN=$TS1
20
  fi
21
  if [ $AZENDE -gt $TS2 ]; then
22
    AZENDE=$TS2
23
  fi
24

25
  echo "Sekunden an diesem Tag: $(($AZENDE - $AZBEGIN)) (von '$(date -d @$AZBEGIN)' bis '$(date -d @$AZENDE)'"
26
  TOTAL=$(($TOTAL + $AZENDE - $AZBEGIN))
27
  
28
  STARTTAG=$(date -d "$STARTTAG + 1 day" +"%Y-%m-%d")
29
done
30

31
echo "TOTAL: $TOTAL"

Vorsicht: Liefert falsche Ergebnisse, wenn sich "date" und "strptime" über die Zeitzone nicht einig sind.

Evtl. erstmal mit strptime oder sed/cut/... die deutsches Zeitstempel in ein ISO8601-Format überführen, und von da an nur noch mit "date" arbeiten.

#7354642
Lesenswert?

Nachtrag:

1
TS1=$(date -d "$(/usr/bin/dateutils.strptime -i '%d.%m.%Y %H:%M' "$DATE1" -f '%Y-%m-%d %H:%M')" +"%s")
2
TS2=$(date -d "$(/usr/bin/dateutils.strptime -i '%d.%m.%Y %H:%M' "$DATE2" -f '%Y-%m-%d %H:%M')" +"%s")
3

4
STARTTAG=$(date -d "@$TS1" +"%Y-%m-%d")
5
ENDTAG=$(date -d "@$TS2" +"%Y-%m-%d")
Gast #7355110
Lesenswert?

Martin schrieb:

Es kann auch sein dass die Zeitstempel nicht in der Arbeitszeit erstellt wurden.

Und woher weisst du, dass die beiden als Start und Stop zusammengehören? Erfasst du die Arbeitszeit nur einmal im Leben?

Wenn sich die angebliche Arbeitszeit bis zum nächsten Tag erstreckt würde ich eher annehmen dass das Abstempeln am vorigen Tag nicht erfolgt ist oder verlorengegangen. Für eine ordnungsgemässe Zeiterfassung müssten die Zeiten als Kommen und Gehen gekennzeichnet sein.

Georg

#7355399
Lesenswert?

Martin schrieb:

zB Date1 20.02.2023 6:35 Date2 21.02.2023 10:04

sollte 8h + 1:04h = 9:04h ergeben.

Nein, da es keinen Sinn macht anzunehmen dass jemand schon um 10:04 morgens die Firma verlässt. Eher schon würde es Sinn ergeben wenn man das als Anfangszeit wertet.

Wie bereits gesagt:

Für eine ordnungsgemässe Zeiterfassung müssten die Zeiten als Kommen und Gehen gekennzeichnet sein.

Gast #7355490
Lesenswert?

Von 9 bis Fünf, geile Arbeitszeit. Raucherpausen inklusive, 30 Minuten Mittag nach 6 Stunden wird dann auch automatisch berechnet? ;) Du "brauchst" ein Kommen/Gehen tagg. Also klar, Brauchste nich, würd' ich aber vorschlagen. Ich hatte sowas in der Art aber auch schonmal programmieren dürfen, als Vierbahnige Stoppuhr für Billardtische (die haben da eben vier Tische). Ich hab UTC-Sekunden genommen und dann die Differenz gebildet und zurückformatiert. War wir am Bequemsten. Hier brauchte ich auch kein Kommen/Gehen. Spielstart, wenn man sich die Kugeln vom Thresen geholt hatte und Spielende inklusive BonDruck mit Preis und Angabe, welcher Tisch, wenn man die Kugeln zurückbrachte. Läuft ganz passabel.

Gast #7356019
Lesenswert?

Hallo.

Es geht nicht um eine Arbeitszeiterfassung sondern um die Reaktionszeit während der Öffnungszeiten. Ich habe es jetzt so versucht: schauen ob die Zeit vor, in oder nach der Öffnunsgzeit ist. Wenn zB vor dann Zeit auf 9:00 verschoben. In kann so bleiben und nach wird auf 9:00 am nächsten Tag gesetzt. Dann schauen ob Sa oder So - wenn ja auf Mo verschieben. Gleiches mit der Endzeit. Jetzt schauen wieviele Tage diff und evtl Wochenende abziehen. Dann ein timediff und am Ende die nicht Arbeitszeit abgezogen.

Martin

#7356486
Lesenswert?

Georg schrieb:

Martin schrieb:

Reaktionszeit während der Öffnungszeiten.

Und die kann sich bis zum nächsten Tag erstrecken? Ein toller Laden.

Wie kommst du darauf, dass es sich um ein Ladengeschäft handelt? Das ist wahrscheinlich genauso falsch wie deine Annahme, es handle sich um eine Arbeitszeiterfassung. Kann auch ein Service-Unternehmen sein, wo jemand anruft, weil seine Klimaanlage kaputt ist und repariert werden muss oder so. Bei sowas sind Reaktionszeiten oft auch vertraglich festgelegt und können sich, sofern kein Notdienst eingerichtet ist, natürlich auch bis zum nächsten Arbeitstag erstrecken.

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren