Måste jag köra mitt bash-script varje minut i crontab för att träffa rätt?

Trädvy Permalänk
Medlem
Plats
Stockholm
Registrerad
Nov 2001

Måste jag köra mitt bash-script varje minut i crontab för att träffa rätt?

Hej,
Fick suverän hjälp här tidigare när jag bråkade med crontab och min utebelysning, och nu är jag här igen.

Det är lite stelt att ha fasta tider konfigurerade i crontab för när lamporna ska tändas och släckas, så jag började fundera. Skulle man inte kunna köra ett script för att ta reda på när solen går ner och upp, och därifrån bestämma sig för när man ska tända och släcka?

Hittade ett script för just tiderna här: http://remco.bierings.eu/?p=9
vilket ger output:

pi@386pi /usr/local/bin/scripts $ sudo ./sunrise.sh sunset # 17:45 pi@386pi /usr/local/bin/scripts $ sudo ./sunrise.sh sunrise # 07:20

Edit: Pillade ihop ett script som kan vara det fulaste, men jag tror att det får lamporna att gå på vid solnedgång och att släckas vid soluppgång.

Men måste jag köra detta i crontab varje minut för att matcha som det är? Hur kan jag få den att kolla så att just den här gången passerades minutvärdet?

#!/bin/bash HSet=$(curl -s http://weather.yahooapis.com/forecastrss?w=906057 | grep astronomy | awk -F\" '{print $4}'|{ date -f - +%H; }) MSet=$(curl -s http://weather.yahooapis.com/forecastrss?w=906057 | grep astronomy | awk -F\" '{print $4}'|{ date -f - +%M; }) HRise=$(curl -s http://weather.yahooapis.com/forecastrss?w=906057 | grep astronomy | awk -F\" '{print $2}'|{ date -f - +%H; $ MRise=$(curl -s http://weather.yahooapis.com/forecastrss?w=906057 | grep astronomy | awk -F\" '{print $2}'|{ date -f - +%M; $ #Hours and minutes now HNow=$(date +%H) Minutes=$(date +%M) #Turn on at sunset if [ $HNow = $HSet ]; then if [ $Minutes = $Mset ]; then /usr/local/bin/tdtool -n 1 fi fi #Turn off at sunrise if [ $HNow = $HRise ]; then if [ $Minutes = $MRise ]; then /usr/local/bin/tdtool -f 1 fi fi exit

Pulade ihop ett script själv som kanske spränger maskinen, men vi får se
Trädvy Permalänk
Medlem
Plats
~
Registrerad
Jul 2001

Har en känsla av att det här kan ge en liten hint: http://www.tldp.org/LDP/abs/html/comparison-ops.html

Fedora, i3wm, Ansible, Vim, git, LaTeX - allt som behövs för att göra mig nöjd.

Trädvy Permalänk
Medlem
Registrerad
Apr 2013
Skrivet av rool:

Hej,
Fick suverän hjälp här tidigare när jag bråkade med crontab och min utebelysning, och nu är jag här igen.

Det är lite stelt att ha fasta tider konfigurerade i crontab för när lamporna ska tändas och släckas, så jag började fundera. Skulle man inte kunna köra ett script för att ta reda på när solen går ner och upp, och därifrån bestämma sig för när man ska tända och släcka?

Hittade ett script för just tiderna här: http://remco.bierings.eu/?p=9
vilket ger output:

pi@386pi /usr/local/bin/scripts $ sudo ./sunrise.sh sunset # 17:45 pi@386pi /usr/local/bin/scripts $ sudo ./sunrise.sh sunrise # 07:20

Edit: Pillade ihop ett script som kan vara det fulaste, men jag tror att det får lamporna att gå på vid solnedgång och att släckas vid soluppgång.

Men måste jag köra detta i crontab varje minut för att matcha som det är? Hur kan jag få den att kolla så att just den här gången passerades minutvärdet?

#!/bin/bash HSet=$(curl -s http://weather.yahooapis.com/forecastrss?w=906057 | grep astronomy | awk -F\" '{print $4}'|{ date -f - +%H; }) MSet=$(curl -s http://weather.yahooapis.com/forecastrss?w=906057 | grep astronomy | awk -F\" '{print $4}'|{ date -f - +%M; }) HRise=$(curl -s http://weather.yahooapis.com/forecastrss?w=906057 | grep astronomy | awk -F\" '{print $2}'|{ date -f - +%H; $ MRise=$(curl -s http://weather.yahooapis.com/forecastrss?w=906057 | grep astronomy | awk -F\" '{print $2}'|{ date -f - +%M; $ #Hours and minutes now HNow=$(date +%H) Minutes=$(date +%M) #Turn on at sunset if [ $HNow = $HSet ]; then if [ $Minutes = $Mset ]; then /usr/local/bin/tdtool -n 1 fi fi #Turn off at sunrise if [ $HNow = $HRise ]; then if [ $Minutes = $MRise ]; then /usr/local/bin/tdtool -f 1 fi fi exit

Crontab är inte enda program i linuxburken som kan köra saker vid en tid utan du har även kommandot at och i ditt fall skulle jag faktiskt kombinera dessa då dom har lite olika styrkor (crontab hanterar repetitiv schemaläggning men det gör inte at). Behåll delen i skriptet som kollar mot när solen går upp och ner men istället för att kolla tider och sen kolla om det är dags så använder du at för att schemalägga tdtool till rätt tid varje dag och kör skriptet bara en gång om dygnet för att göra detta.

Trädvy Permalänk
Medlem
Plats
Stockholm
Registrerad
Nov 2001

@aluser: Aha, så jag skulle kunna köra ett script med cron vid typ 00:01 som gräver fram när solen kommer att gå upp och ner det här dygnet, mata de tiderna som argument till två "at"-jobb och sen glida vidare?

Trädvy Permalänk
Medlem
Plats
Stockholm
Registrerad
Nov 2001

@Crazy Ferret: Ja, jag kollade på det där, men fick inte ordning på det eftersom det verkar vara strängar och inte värden jag får ut i mina variabler.

Trädvy Permalänk
Medlem
Registrerad
Apr 2013
Skrivet av rool:

@aluser: Aha, så jag skulle kunna köra ett script med cron vid typ 00:01 som gräver fram när solen kommer att gå upp och ner det här dygnet, mata de tiderna som argument till två "at"-jobb och sen glida vidare?

Precis

Trädvy Permalänk
Medlem
Plats
~
Registrerad
Jul 2001
Skrivet av rool:

@Crazy Ferret: Ja, jag kollade på det där, men fick inte ordning på det eftersom det verkar vara strängar och inte värden jag får ut i mina variabler.

Scrolla ner så ser du att där även finns jämförelseoperatorer för strängar, vilket fungerar utmärkt utifrån min lilla testbänk baserad på en reducerad variant av ditt script:

#!/bin/bash HSet=$(curl -s http://weather.yahooapis.com/forecastrss?w=906057 | grep astronomy | awk -F\" '{print $4}'|{ date -f - +%H; }) #Hours and minutes now HNow=$(date +%H) #HSet=23 #Uncomment to test with different values echo "HSet:" $HSet ", HNow:" $HNow if [ "$HNow" = "$HSet" ]; then echo "Test1 '=': HNow == HSet" else echo "Test1 '=': HNow != HSet" fi if [[ "$HNow" < "$HSet" ]]; then echo "Test2 '<': HNow < HSet" else echo "Test2 '<': HNow >= HSet" fi if [[ "$HNow" > "$HSet" ]]; then echo "Test2 '>': HNow > HSet" else echo "Test2 '>': HNow =< HSet" fi exit

Längre än så kan jag inte hjälpa dig för stunden då schemaläggning inte är något jag fördjupat mig i alls.

Fedora, i3wm, Ansible, Vim, git, LaTeX - allt som behövs för att göra mig nöjd.

Trädvy Permalänk
Forumledare
Registrerad
Okt 2002

Soluppgång och -nedgång kan man beräkna hjälpligt själv, utan att behöva gå över internet och Yahoo. "Själv" syftar här på att någon annan redan har gjort det; exempelvis i Perlmodulen DateTime::Astro::Sunrise.

  1. Installera paketet libdatetime-astro-sunrise-perl.

  2. Spara nedanstående snabbsnickrade skript (varning för undermålig testning) som ~/bin/atsunrisesunset.pl:

    #!/usr/bin/env perl use strict; use warnings; use DateTime::TimeZone; use DateTime::Astro::Sunrise; use File::Basename; use Scalar::Util qw/looks_like_number/; my $at = '/usr/bin/at'; my $time_format = '%H:%M %Y-%m-%d'; sub usage { my $script_name = basename($0); print STDERR <<" USAGE"; Schedule jobs with $at at sunrise and sunset of the current day. usage: $script_name LATITUDE LONGITUDE SUNRISE_JOB_FILE SUNSET_JOB_FILE $script_name LATITUDE LONGITUDE The first form schedules the given jobs at sunrise and sunset of current day. The second form prints a debug message with the times that would be used. LATITUDE and LONGITUDE are decimal degree representations of latitude and longitude of where wanted sunrise and sunset times are to be calculated. SUNRISE_JOB_FILE and SUNSET_JOB_FILE are job files suited for use with `at`. USAGE exit 1; } sub debug { my ($sunrise_time, $sunset_time) = sunrise_and_sunset_times(@_); print <<" DEBUG"; Debug info ---------- Calculated sunrise for today: $sunrise_time Calculated sunset for today: $sunset_time DEBUG exit; } sub sunrise_and_sunset_times { my ($latitude, $longitude) = @_; unless (looks_like_number($latitude) && looks_like_number($longitude)) { usage(); } my $dt = DateTime->now; my $tz = DateTime::TimeZone->new(name => 'local'); $dt->set_time_zone($tz); my $dt_a_s = DateTime::Astro::Sunrise->new($longitude, $latitude); my @times = $dt_a_s->sunrise($dt); foreach my $time (@times) { $time->set_time_zone($tz) } return @times; } sub at_schedule { my ($time, $job_file) = @_; system($at, $time->strftime($time_format), '-f', $job_file); } sub parse_cli { my $argc = $#ARGV + 1; if ($argc == 2) { debug(@ARGV) } elsif ($argc == 4) { return @ARGV } else { usage() } } sub main { my ($longitude, $latitude, $sunrise_jobs, $sunset_jobs) = parse_cli(); my ($sunrise, $sunset) = sunrise_and_sunset_times($latitude, $longitude); foreach my $at_cmd ([$sunrise, $sunrise_jobs], [$sunset, $sunset_jobs]) { at_schedule(@$at_cmd); } } main();

    Dold text
  3. Gör skriptet exekverbart:

    chmod +x ~/bin/atsunrisesunset.pl

    Ifall du kör skriptet med två parametrar (latitud och longitud) så skriver det ut de tider som räknats ut för den aktuella dagen, vilket kan vara bra för en rimlighetskontroll. Exempel för Stockholm:

    $ ~/bin/atsunrisesunset.pl 59.3294 18.0686 Debug info ---------- Calculated sunrise for today: 2015-10-15T07:22:00 Calculated sunset for today: 2015-10-15T17:44:00

    Körs skriptet med fyra parametrar som beskriver latitud, longitud, samt jobbfiler för soluppgång respektive -nedgång så köas dessa jobbfiler med at vid motsvarande tider. Enklast körs skriptet strax efter midnatt.

  4. Skapa dina jobbfiler /path/to/sunrise_job_file respektive /path/to/sunset_job_file (med sökvägar enligt eget tycke). Notera att dina "jobbfiler" bara ska innehålla namnen på de skript du faktiskt vill köra, snarare än skriptlogiken i sig. Är det triviala skript så går det visserligen att köra dem direkt i denna fil, "men det är inte rätt" . Jag skrev lite längre om detta en annan gång på forumet.

  5. Kör följande i din användares crontab:

    5 0 * * * /home/användare/bin/atsunrisesunset.pl 59.3294 18.0686 /path/to/sunrise_job_file /path/to_sunset_job_file 2>/dev/null

    Fem minuter över midnatt varje dag så bör då cron se till att dina at-körningar adderas.

Spontana förbättringsidéer som lämnas som övningar åt läsaren;

  • Vettig felrapportering ifall at-körningarna misslyckas.

  • Varningstext för folk boende norr/söder om respektive polcirkel…

Konsekvens i föreslaget skriptnamn.

Nu med kortare användarnamn, men fortfarande bedövande långa inlägg.