@ -0,0 +1,59 @@ |
|||||
|
#!/usr/bin/perl |
||||
|
# (c) Pali 2019, Perl license |
||||
|
|
||||
|
use strict; |
||||
|
use warnings; |
||||
|
|
||||
|
use Net::Telnet; |
||||
|
use Time::HiRes qw(usleep); |
||||
|
|
||||
|
die "Usage: $0 host pass line 0|1\n" unless @ARGV == 4; |
||||
|
my $host = $ARGV[0]; |
||||
|
my $pass = $ARGV[1]; |
||||
|
my $line = $ARGV[2]; |
||||
|
my $enable = $ARGV[3]; |
||||
|
|
||||
|
die "Line $line is not valid line number [1-6]\n" unless $line =~ /^[1-6]$/; |
||||
|
|
||||
|
my $t = Net::Telnet->new(Timeout => 3, Prompt => '/[^\n]*> $/'); |
||||
|
|
||||
|
$t->open($host); |
||||
|
$t->waitfor('/Password :$/'); |
||||
|
$t->print($pass); |
||||
|
$t->waitfor($t->prompt); |
||||
|
|
||||
|
my $failed; |
||||
|
my $skip; |
||||
|
my $auto_answer; |
||||
|
|
||||
|
for (1..10) { |
||||
|
if ($_ == 10) { |
||||
|
$failed = 1; |
||||
|
last; |
||||
|
} |
||||
|
|
||||
|
($auto_answer) = map { /^auto_answer : ([0-9]+)$/ ? $1 : () } $t->cmd('show config'); |
||||
|
if ($enable and ($auto_answer & (1 << ($line - 1)))) { |
||||
|
do { print "auto_answer on $host is already enabled\n"; $skip = 1 } if $_ == 1; |
||||
|
last; |
||||
|
} elsif (not $enable and not ($auto_answer & (1 << ($line - 1)))) { |
||||
|
do { print "auto_answer on $host is already disabled\n"; $skip = 1 } if $_ == 1; |
||||
|
last; |
||||
|
} |
||||
|
|
||||
|
foreach ('open', 'key dir', 'key set', 'key set', 'key soft4', 'key set', 'key 6', 'key 8', "key $line", 'key soft1', 'key soft2', 'key set', 'close') { |
||||
|
$t->cmd("test $_"); |
||||
|
usleep 200_000; |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
$t->print("exit"); |
||||
|
$t->close(); |
||||
|
|
||||
|
if ($failed) { |
||||
|
warn (($enable ? "enabling" : "disabling") . " auto_answer on $host failed\n"); |
||||
|
exit 1; |
||||
|
} else { |
||||
|
print ("auto_answer on $host is now " . ($enable ? "enabled" : "disabled") . "\n") unless $skip; |
||||
|
exit 0; |
||||
|
} |
@ -0,0 +1,25 @@ |
|||||
|
#!/usr/bin/perl |
||||
|
# (c) Pali 2019, Perl license |
||||
|
|
||||
|
use strict; |
||||
|
use warnings; |
||||
|
|
||||
|
use Net::Telnet; |
||||
|
|
||||
|
die "Usage: $0 host pass\n" unless @ARGV == 2; |
||||
|
my $host = $ARGV[0]; |
||||
|
my $pass = $ARGV[1]; |
||||
|
|
||||
|
my $t = Net::Telnet->new(Timeout => 3, Prompt => '/[^\n]*> $/'); |
||||
|
|
||||
|
$t->open($host); |
||||
|
$t->waitfor('/Password :$/'); |
||||
|
$t->print($pass); |
||||
|
$t->waitfor($t->prompt); |
||||
|
|
||||
|
$t->cmd('erase protflash'); |
||||
|
|
||||
|
# TODO: check if erase was allowed |
||||
|
|
||||
|
$t->print('exit'); |
||||
|
$t->close(); |
@ -0,0 +1,24 @@ |
|||||
|
#!/usr/bin/perl |
||||
|
# (c) Pali 2019, Perl license |
||||
|
|
||||
|
use strict; |
||||
|
use warnings; |
||||
|
|
||||
|
use Net::Telnet; |
||||
|
|
||||
|
die "Usage: $0 host pass\n" unless @ARGV == 2; |
||||
|
my $host = $ARGV[0]; |
||||
|
my $pass = $ARGV[1]; |
||||
|
|
||||
|
my $t = Net::Telnet->new(Timeout => 3, Prompt => '/[^\n]*> $/'); |
||||
|
|
||||
|
$t->open($host); |
||||
|
$t->waitfor('/Password :$/'); |
||||
|
$t->print($pass); |
||||
|
$t->waitfor($t->prompt); |
||||
|
|
||||
|
$t->print('reset'); |
||||
|
|
||||
|
# TODO: check if reset was allowed |
||||
|
|
||||
|
$t->close(); |
@ -0,0 +1,23 @@ |
|||||
|
#!/usr/bin/perl |
||||
|
# (c) Pali 2019, Perl license |
||||
|
|
||||
|
use strict; |
||||
|
use warnings; |
||||
|
|
||||
|
use Net::Telnet; |
||||
|
|
||||
|
die "Usage: $0 host pass\n" unless @ARGV == 2; |
||||
|
my $host = $ARGV[0]; |
||||
|
my $pass = $ARGV[1]; |
||||
|
|
||||
|
my $t = Net::Telnet->new(Timeout => 3, Prompt => '/[^\n]*> $/'); |
||||
|
|
||||
|
$t->open($host); |
||||
|
$t->waitfor('/Password :$/'); |
||||
|
$t->print($pass); |
||||
|
$t->waitfor($t->prompt); |
||||
|
|
||||
|
print "$_\n" foreach grep !/^(?:Current Phone Status|--------------------|I100 No errors|)$/, map { /^[\x00-\x31\s]*(.*?)\s*$/s; $1 } $t->cmd('show status'); |
||||
|
|
||||
|
$t->print("exit"); |
||||
|
$t->close(); |
@ -0,0 +1,29 @@ |
|||||
|
#!/usr/bin/perl |
||||
|
# (c) Pali 2019, Perl license |
||||
|
|
||||
|
use strict; |
||||
|
use warnings; |
||||
|
|
||||
|
use Net::Telnet; |
||||
|
use Time::HiRes qw(usleep); |
||||
|
|
||||
|
die "Usage: $0 host pass volume\n" unless @ARGV == 3; |
||||
|
my $host = $ARGV[0]; |
||||
|
my $pass = $ARGV[1]; |
||||
|
my $vol = $ARGV[2]; |
||||
|
|
||||
|
my $t = Net::Telnet->new(Timeout => 3, Prompt => '/[^\n]*> $/'); |
||||
|
|
||||
|
$t->open($host); |
||||
|
$t->waitfor('/Password :$/'); |
||||
|
$t->print($pass); |
||||
|
$t->waitfor($t->prompt); |
||||
|
|
||||
|
foreach ('open', ('key voldn') x 16, ('key volup') x $vol, 'close') { |
||||
|
$t->cmd("test $_"); |
||||
|
usleep 200_000; |
||||
|
} |
||||
|
|
||||
|
$t->print("exit"); |
||||
|
$t->close(); |
||||
|
|
@ -0,0 +1,54 @@ |
|||||
|
#!/usr/bin/perl |
||||
|
# (c) Pali 2019, Perl license |
||||
|
|
||||
|
use strict; |
||||
|
use warnings; |
||||
|
|
||||
|
use Net::SIP; |
||||
|
use Net::SIP::Util qw(laddr4dst INETSOCK ip_sockaddr2parts); |
||||
|
use Socket; |
||||
|
|
||||
|
die "Usage: $0 host line\n" unless @ARGV == 2; |
||||
|
my $host = $ARGV[0]; |
||||
|
my $line = $ARGV[1]; |
||||
|
|
||||
|
my $ip = inet_aton($host); |
||||
|
die "ERROR: Cannot resolve host\n" unless defined $ip; |
||||
|
my $addr = inet_ntoa($ip); |
||||
|
|
||||
|
my $laddr = laddr4dst($addr); |
||||
|
die "ERROR: No route to host\n" unless $laddr; |
||||
|
|
||||
|
my $sock = INETSOCK(Proto => 'udp', LocalAddr => $laddr, LocalPort => 0); |
||||
|
die "ERROR: Cannot create socket: $!\n" unless $sock; |
||||
|
|
||||
|
my $lport = (ip_sockaddr2parts(getsockname($sock)))[1]; |
||||
|
|
||||
|
my $leg = Net::SIP::Leg->new(sock => $sock); |
||||
|
die "ERROR: Cannot create leg: $!\n" unless $leg; |
||||
|
|
||||
|
my $ua = Net::SIP::Simple->new(from => "<sip:root\@$laddr:$lport>", leg => $leg); |
||||
|
die "ERROR: Cannot create SIP user agent: $!\n" unless $ua; |
||||
|
|
||||
|
my ($stop, $code, $text); |
||||
|
|
||||
|
$ua->{endpoint}->new_request( |
||||
|
'NOTIFY', |
||||
|
{ from => $ua->{from}, to => "<sip:$line\@$host>" }, |
||||
|
sub { |
||||
|
(undef, undef, undef, $code, my $packet) = @_; |
||||
|
(undef, $text) = $packet ? $packet->as_parts : (); |
||||
|
$stop = 1; |
||||
|
}, |
||||
|
'', |
||||
|
uri => "sip:$line\@$addr", |
||||
|
Event => 'check-sync', |
||||
|
Contact => $ua->{from}, |
||||
|
); |
||||
|
|
||||
|
$ua->loop(3, \$stop); |
||||
|
$ua->cleanup(); |
||||
|
|
||||
|
die "ERROR: Timeout\n" unless $stop; |
||||
|
die "ERROR: Invalid response\n" unless $code and $text; |
||||
|
die "ERROR: SIP response: $code $text\n" unless $code eq '200'; |
@ -0,0 +1,33 @@ |
|||||
|
#!/usr/bin/perl |
||||
|
# (c) Pali 2019, Perl license |
||||
|
|
||||
|
use strict; |
||||
|
use warnings; |
||||
|
|
||||
|
use Net::Telnet; |
||||
|
use Time::HiRes qw(usleep); |
||||
|
|
||||
|
die "Usage: $0 host pass ast_user\n" unless @ARGV == 3; |
||||
|
my $host = $ARGV[0]; |
||||
|
my $pass = $ARGV[1]; |
||||
|
my $user = $ARGV[2]; |
||||
|
|
||||
|
my $t = Net::Telnet->new(Timeout => 3, Prompt => '/[^\n]*> $/'); |
||||
|
|
||||
|
$t->open($host); |
||||
|
$t->waitfor('/Password :$/'); |
||||
|
$t->print($pass); |
||||
|
$t->waitfor($t->prompt); |
||||
|
|
||||
|
foreach ('open', ('key volup') x 16, 'close') { |
||||
|
if (system('sh', '-c', qq[asterisk -rx "core show channels" |grep -q "$user"]) != 0) { |
||||
|
print STDERR "Call ended, exiting"; |
||||
|
last; |
||||
|
} |
||||
|
$t->cmd("test $_"); |
||||
|
usleep 200_000; |
||||
|
} |
||||
|
|
||||
|
$t->print("exit"); |
||||
|
$t->close(); |
||||
|
|
@ -0,0 +1,6 @@ |
|||||
|
#!/bin/sh |
||||
|
pass=`sed -n 's/telnet_pass=//p' config.txt` |
||||
|
ip=`sed -n 's/server_ip=//p' config.txt | sed 's/\.[0-9]*$//'` |
||||
|
for i in `cat phones.txt | grep -v \- | sed -n 's/^\([0-9][0-9]\).*/\1/p'`; do |
||||
|
{ admin_scripts/send_reboot.pl "$ip.$i" "$i" 2>&1 || admin_scripts/force_reboot.pl "$ip.$i" "$pass" 2>&1 ; } | sed "s/^/$i: /" |
||||
|
done |
@ -0,0 +1,14 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
line="$1" |
||||
|
[[ -n "$line" ]] || { echo >&2 "usage: $0 <line>"; exit 1; } |
||||
|
|
||||
|
echo "Action: login |
||||
|
username: admin |
||||
|
secret: admin |
||||
|
events: off |
||||
|
|
||||
|
Action: hangup |
||||
|
Channel: /PJSIP/emerg$line-.*/ |
||||
|
" | socat - TCP:localhost:5038 |
||||
|
|
@ -0,0 +1,11 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
cd "$(dirname "$0")" |
||||
|
echo "Action: login |
||||
|
username: admin |
||||
|
secret: admin |
||||
|
events: off |
||||
|
|
||||
|
Action: hangup |
||||
|
Channel: /.*emerg.*/ |
||||
|
" | socat - TCP:localhost:5038 |
@ -0,0 +1,21 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
cd "$(dirname "$0")" |
||||
|
line="$1" |
||||
|
. config.txt |
||||
|
|
||||
|
./ann_end.sh "$line" # and any existing calls to prevent our call ending up in "call waiting" state (and thus not autoanswered) |
||||
|
sleep 0.5 |
||||
|
./autoanswer_line.sh "$line" 1 || { echo >&2 "failed to enable autoanswer, exiting."; exit 1; } |
||||
|
|
||||
|
fn=/var/spool/asterisk/tmp/ann_$line.call |
||||
|
echo " |
||||
|
Channel: PJSIP/emerg$line |
||||
|
Context: emerg_listen |
||||
|
Extension: 120 |
||||
|
Priority: 1 |
||||
|
" >$fn |
||||
|
|
||||
|
mv "$fn" /var/spool/asterisk/outgoing/ |
||||
|
|
||||
|
./ann_volup.sh "$line" & |
@ -0,0 +1,5 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
cd "$(dirname "$0")" |
||||
|
cat phones.txt | awk '{print $1}' | grep '^[3-5]' | xargs -n1 -P0 ./ann_listen.sh |
||||
|
|
@ -0,0 +1,30 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
# By default, we operate in bracketed mode: initiate listening calls, play announcement and terminate them |
||||
|
# With -n, we do not do bracketing, you have to initiate and terminate listening calls yourself |
||||
|
# with ann_listen[_all].sh and ann_end[_all].sh. Useful if you want to combine playback and speech in |
||||
|
# one announcement (call 121 to speak without bracketing). |
||||
|
|
||||
|
if [[ "$1" == -n ]]; then num=121; shift; else num=122; fi |
||||
|
|
||||
|
|
||||
|
playstring="silence/1" |
||||
|
i=0 |
||||
|
for arg in "$@"; do |
||||
|
if [[ "$arg" =~ ^silence ]]; then |
||||
|
playitem="$arg" |
||||
|
else |
||||
|
ffmpeg -i "$arg" -ar 8000 -ac 1 -y /tmp/ann$i.wav |
||||
|
playitem=/tmp/ann$i |
||||
|
fi |
||||
|
playstring="$playstring&$playitem" |
||||
|
i=$((i+1)) |
||||
|
done |
||||
|
|
||||
|
fn=/var/spool/asterisk/tmp/ann_play.call |
||||
|
echo " |
||||
|
Channel: Local/$num@orgs |
||||
|
Application: Playback |
||||
|
Data: $playstring |
||||
|
" >$fn |
||||
|
mv $fn /var/spool/asterisk/outgoing/ |
@ -0,0 +1,36 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
cd "$(dirname "$0")" |
||||
|
line="$1" |
||||
|
snd="$2" |
||||
|
. config.txt |
||||
|
|
||||
|
./ann_end.sh "$line" # and any existing calls to prevent our call ending up in "call waiting" state (and thus not autoanswered) |
||||
|
sleep 0.5 |
||||
|
./autoanswer_line.sh "$line" 1 || { echo >&2 "failed to enable autoanswer, exiting."; exit 1; } |
||||
|
|
||||
|
playstring="silence/1" |
||||
|
i=0 |
||||
|
for arg in "$@"; do |
||||
|
if [[ "$arg" =~ ^silence ]]; then |
||||
|
playitem="$arg" |
||||
|
else |
||||
|
ffmpeg -i "$arg" -ar 8000 -ac 1 -y /tmp/ann${line}_$i.wav |
||||
|
playitem=/tmp/ann${line}_$i |
||||
|
fi |
||||
|
playstring="$playstring&$playitem" |
||||
|
i=$((i+1)) |
||||
|
done |
||||
|
|
||||
|
fn=/var/spool/asterisk/tmp/ann_$line.call |
||||
|
echo " |
||||
|
Channel: PJSIP/emerg$line |
||||
|
Application: Playback |
||||
|
Data: $playstring |
||||
|
Priority: 1 |
||||
|
" >$fn |
||||
|
|
||||
|
mv "$fn" /var/spool/asterisk/outgoing/ |
||||
|
|
||||
|
./ann_volup.sh "$line" & |
||||
|
|
@ -0,0 +1,18 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
cd "$(dirname "$0")" |
||||
|
./ann_end_all.sh |
||||
|
echo "Action: login |
||||
|
username: admin |
||||
|
secret: admin |
||||
|
events: off |
||||
|
|
||||
|
Action: hangup |
||||
|
Channel: /.*emerg.*/ |
||||
|
|
||||
|
Action: ConfbridgeKick |
||||
|
Conference: 120 |
||||
|
Channel: all |
||||
|
|
||||
|
" | socat - TCP:localhost:5038 |
||||
|
|
@ -0,0 +1,18 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
cd "$(dirname "$0")" |
||||
|
line="$1" |
||||
|
[[ "$line" =~ ^[0-9]+$ ]] || { echo >&2 "usage: $0 <line>"; exit 1; } |
||||
|
. config.txt |
||||
|
ip_prefix=${server_ip%.*} |
||||
|
ip="$ip_prefix.$line" |
||||
|
|
||||
|
for i in $(seq 1 10); do |
||||
|
if asterisk -rx "core show channels" |grep -q "emerg$line"; then |
||||
|
./admin_scripts/volume_up.pl "$ip" "$telnet_pass" "emerg$line" |
||||
|
break |
||||
|
else |
||||
|
sleep 1 |
||||
|
fi |
||||
|
done |
||||
|
|
@ -0,0 +1,15 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
state="$1" |
||||
|
|
||||
|
case $state in |
||||
|
1) |
||||
|
gr=enabled |
||||
|
;; |
||||
|
0) |
||||
|
gr=disabled |
||||
|
;; |
||||
|
esac |
||||
|
|
||||
|
cd /opt/ksp |
||||
|
cat phones.txt | awk '{print $1}' | grep '^[3-5]' | xargs -i -n1 -P0 ./autoanswer_line.sh '{}' "$state" | grep $gr | cut -d. -f4| cut -d' ' -f1 |
@ -0,0 +1,12 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
cd "$(dirname "$0")" |
||||
|
line="$1" |
||||
|
state="$2" |
||||
|
{ [[ "$line" =~ ^[0-9]+$ ]] && [[ "$state" =~ ^[01]$ ]]; } || { echo >&2 "usage: $0 <line> <0|1>"; exit 1; } |
||||
|
. config.txt |
||||
|
ip_prefix=${server_ip%.*} |
||||
|
ip="$ip_prefix.$line" |
||||
|
|
||||
|
./admin_scripts/auto_answer.pl "$ip" "$telnet_pass" 2 "$state" |
||||
|
|
@ -0,0 +1,24 @@ |
|||||
|
veřejné číslo pro volání zvenku: 910 128 976 |
||||
|
|
||||
|
0 - 9 - nič |
||||
|
20 - 29 - ORG cisco telefóny |
||||
|
30 - 59 - zvyšné cisco telefóny |
||||
|
60 - 99 - zvyšné ne-cisco telefóny (ak budeme zapájať iných SIP klientov) |
||||
|
78 - (mnemonic: "su") Volání org-only čísel z libovolného telefonu, případně zvenku |
||||
|
100 - 199 - čísla pre automaty, odkazové schránky a iné veci |
||||
|
- 11x... veřejné konference |
||||
|
- 12x announce mechanismus |
||||
|
- 120 announce listen |
||||
|
- 121 [org only] announce speak (jen umožňuje mluvit k posluchačům) |
||||
|
- 122 [org only] announce (připoj všechny účastníky do konference a pak mluv) |
||||
|
- 123xx [org only] unicast announce na telefon xx (funguje obousměrně; nezneužívat k odposlechu, ale můžete se bavit s účastníky) |
||||
|
- 130 - vytočí náhodnú non-ORG linku |
||||
|
- 131 - vyzvednutí hlasových zpráv |
||||
|
- 14xx - přímé zanechání hlasové zprávy pro linku xx |
||||
|
- 16x - IVR |
||||
|
- 161 - FBI |
||||
|
|
||||
|
Podle samolepek na telefonu: |
||||
|
|
||||
|
8888 - helpdesk -> FBI |
||||
|
4445 - HR -> přečtení pokynů |
@ -0,0 +1,2 @@ |
|||||
|
#!/bin/sh |
||||
|
rm -f etc_asterisk/pjsip_wizard_phones.conf etc_asterisk/voicemail_gen.conf tftp_reflash/SIP00*.cnf tftp_reflash/SIPDefault.cnf tftp/Phones/SIP00*.cnf tftp/RINGLIST.DAT etc_dnsmasq.d/phones.conf www/directory.txt etc_asterisk/voicemail_gen.conf |
@ -0,0 +1,4 @@ |
|||||
|
server_ip=172.16.0.1 |
||||
|
telnet_pass=FIXME |
||||
|
hmac_key=FIXME |
||||
|
fake_year=2114 |
@ -0,0 +1,8 @@ |
|||||
|
#!/bin/sh -e |
||||
|
if test "$#" != "1"; then echo "Usage: $0 sound_file.ext"; exit 1; fi |
||||
|
file="${1%.*}.pcm" |
||||
|
ffmpeg -loglevel fatal -y -i "$1" -f u8 -c pcm_mulaw -ar 8000 -ac 1 "$file" |
||||
|
size=`du -b "$file" | cut -f1` |
||||
|
size=$(($size/240*240)) |
||||
|
if test "$size" -gt "16080"; then size=16080; fi |
||||
|
truncate -s "$size" "$file" |
@ -0,0 +1,22 @@ |
|||||
|
[default_bridge] |
||||
|
type=bridge |
||||
|
video_mode=none |
||||
|
|
||||
|
[ann_listen] |
||||
|
type=user |
||||
|
startmuted=yes |
||||
|
quiet=yes |
||||
|
announce_only_user=no |
||||
|
|
||||
|
[ann_speak] |
||||
|
type=user |
||||
|
quiet=yes |
||||
|
announce_only_user=no |
||||
|
startmuted=no |
||||
|
|
||||
|
[ann] |
||||
|
type=bridge |
||||
|
video_mode=none |
||||
|
|
||||
|
[empty_menu] |
||||
|
type=menu |
@ -0,0 +1,141 @@ |
|||||
|
extensions = {} |
||||
|
extensions.participants = {} |
||||
|
extensions.orgs = {} |
||||
|
extensions.emerg = {} |
||||
|
extensions.emerg_listen = {} |
||||
|
extensions.ann_bracket = {} |
||||
|
extensions.odorik = {} |
||||
|
extensions.external = {} |
||||
|
|
||||
|
function sip_exten(ch, ext) |
||||
|
app.dial("PJSIP/" .. ext, 40) |
||||
|
local status = channel.DIALSTATUS:get() |
||||
|
app.verbose("status: " .. status) |
||||
|
if status == "BUSY" then |
||||
|
flags="b" |
||||
|
else |
||||
|
flags="u" |
||||
|
end |
||||
|
app.voicemail(ext, flags) |
||||
|
end |
||||
|
function ann_unicast(ch, ext) |
||||
|
app.dial("PJSIP/emerg" .. string.sub(ext, 4)) |
||||
|
end |
||||
|
function sip_nightmode(ch, ext) |
||||
|
local hour = tonumber(os.date("%H")) |
||||
|
local minute = tonumber(os.date("%M")) |
||||
|
if hour < 12 or (hour == 12 and minute < 10) or hour > 23 or (hour == 23 and minute > 20) then |
||||
|
app.playback("/opt/ksp/sounds/nocni_klid") |
||||
|
app.voicemail(ext) |
||||
|
else |
||||
|
sip_exten(ch, ext) |
||||
|
end |
||||
|
end |
||||
|
function voicemail_direct(ch, ext) |
||||
|
app.voicemail(string.sub(ext, 3)) |
||||
|
end |
||||
|
function voicemail_listen(ch, ext) |
||||
|
local caller = channel.CALLERID("num"):get() |
||||
|
app.voicemailmain(caller, "s") -- no password prompt |
||||
|
end |
||||
|
|
||||
|
function conf(ch, ext) |
||||
|
app.confbridge(ext) |
||||
|
end |
||||
|
|
||||
|
function add(ctxs, ext, func) |
||||
|
for i = 1, #ctxs do |
||||
|
extensions[ctxs[i]][ext] = func |
||||
|
end |
||||
|
end |
||||
|
|
||||
|
function ann_listen(ch, ext) |
||||
|
app.confbridge("120", "ann", "ann_listen", "empty_menu") |
||||
|
end |
||||
|
function ann_speak(ch, ext) |
||||
|
app.confbridge("120", "ann", "ann_speak") |
||||
|
end |
||||
|
|
||||
|
function ann_bracket(ch, ext) |
||||
|
app.system("/opt/ksp/ann_listen_all.sh") |
||||
|
app.confbridge("120", "ann", "ann_speak") |
||||
|
end |
||||
|
function ann_bracket_hangup(ch, ext) |
||||
|
app.system("/opt/ksp/ann_end_all.sh") |
||||
|
end |
||||
|
function ann_bracket_goto(ch, ext) |
||||
|
app.goto("ann_bracket", "122", 1) |
||||
|
end |
||||
|
|
||||
|
function fbi(ch, ext) |
||||
|
app.dial("PJSIP/910119352@odorik") |
||||
|
end |
||||
|
|
||||
|
function odorik_incoming(ch, ext) |
||||
|
app.answer() |
||||
|
app.read("klapka", "/opt/ksp/sounds/klapka") |
||||
|
local klapka = channel.klapka:get() |
||||
|
app.goto("external", klapka, 1) |
||||
|
end |
||||
|
|
||||
|
function su(ch, ext) |
||||
|
app.read("heslo", "/opt/ksp/sounds/heslo") |
||||
|
local heslo = channel.heslo:get() |
||||
|
if heslo == "2886287" then |
||||
|
app.read("klapka", "/opt/ksp/sounds/klapka") |
||||
|
local klapka = channel.klapka:get() |
||||
|
app.goto("orgs", klapka, 1) |
||||
|
else |
||||
|
app.playback("/opt/ksp/sounds/spatne_heslo") |
||||
|
app.hangup() |
||||
|
end |
||||
|
end |
||||
|
|
||||
|
--http://lua-users.org/wiki/StringTrim |
||||
|
function trim1(s) |
||||
|
return (s:gsub("^%s*(.-)%s*$", "%1")) |
||||
|
end |
||||
|
function call_rand(ch, ext) |
||||
|
local caller = channel.CALLERID("num"):get():gsub("'", "") |
||||
|
local handle = io.popen("/opt/ksp/rand_line.sh '" .. caller .. "'") |
||||
|
local line = trim1(handle:read("*all")) |
||||
|
handle:close() |
||||
|
app.verbose("RAND: " .. line) |
||||
|
app.dial("PJSIP/"..line) |
||||
|
end |
||||
|
function snd(name) |
||||
|
return function(ch, ext) |
||||
|
app.answer() |
||||
|
app.playback("/opt/ksp/sounds/" .. name) |
||||
|
app.hangup() |
||||
|
end |
||||
|
end |
||||
|
|
||||
|
add({"orgs"}, "_2X", sip_exten) -- org phones |
||||
|
add({"orgs"}, "_[345]X", sip_exten) -- participant phones |
||||
|
-- night mode restriction applies only when calling from participant phones |
||||
|
add({"participants", "external"}, "_2X", sip_nightmode) -- org phones |
||||
|
add({"participants", "external"}, "_[345]X", sip_nightmode) -- participant phones |
||||
|
add({"orgs", "participants", "external"}, "_11.", conf) |
||||
|
add({"orgs", "participants", "emerg_listen", "external"}, "120", ann_listen) |
||||
|
add({"orgs"}, "121", ann_speak) |
||||
|
-- Because hangup actions are per-context and not per-extension, we need to jump to |
||||
|
-- a separate context to allow a hangup handler to terminate listeners after a call |
||||
|
-- to 122 is done. |
||||
|
add({"orgs"}, "122", ann_bracket_goto) |
||||
|
add({"ann_bracket"}, "122", ann_bracket) |
||||
|
add({"ann_bracket"}, "h", ann_bracket_hangup) |
||||
|
add({"orgs"}, "_123XX", ann_unicast) |
||||
|
add({"orgs", "participants"}, "131", voicemail_listen) -- does not work, done in extensions.conf!! |
||||
|
add({"orgs", "participants", "external"}, "_14XX", voicemail_direct) |
||||
|
add({"participants", "external"}, "78", su) |
||||
|
add({"odorik"}, "s", odorik_incoming) |
||||
|
add({"orgs", "participants", "external"}, "160", fbi) |
||||
|
add({"orgs", "participants", "external"}, "910119352", fbi) |
||||
|
-- Na některých telefonech je od původních majitelů nálepka "call helpdesk at 8888" |
||||
|
add({"orgs", "participants", "external"}, "8888", fbi) |
||||
|
add({"orgs", "participants", "external"}, "4445", snd("hr")) |
||||
|
add({"orgs", "participants", "external"}, "130", call_rand) |
||||
|
|
||||
|
|
||||
|
--add({"orgs", "participants"}, "_131", snd("sadtromb")) |
@ -0,0 +1,3 @@ |
|||||
|
[logfiles] |
||||
|
|
||||
|
console => notice,warning,error,debug,verbose |
@ -0,0 +1,11 @@ |
|||||
|
[general] |
||||
|
enabled = yes |
||||
|
webenabled = no |
||||
|
|
||||
|
port = 5038 |
||||
|
bindaddr = 127.0.0.1 |
||||
|
|
||||
|
[admin] |
||||
|
secret = admin |
||||
|
read = all |
||||
|
write = all |
@ -0,0 +1,73 @@ |
|||||
|
; |
||||
|
; Asterisk configuration file |
||||
|
; |
||||
|
; Module Loader configuration file |
||||
|
; |
||||
|
|
||||
|
[modules] |
||||
|
autoload=yes |
||||
|
; |
||||
|
; Any modules that need to be loaded before the Asterisk core has been |
||||
|
; initialized (just after the logger has been initialized) can be loaded |
||||
|
; using 'preload'. This will frequently be needed if you wish to map all |
||||
|
; module configuration files into Realtime storage, since the Realtime |
||||
|
; driver will need to be loaded before the modules using those configuration |
||||
|
; files are initialized. |
||||
|
; |
||||
|
; An example of loading ODBC support would be: |
||||
|
;preload => res_odbc.so |
||||
|
;preload => res_config_odbc.so |
||||
|
; |
||||
|
; If you want, load the GTK console right away. |
||||
|
; Don't load the KDE console since |
||||
|
; it's not as sophisticated right now. |
||||
|
; |
||||
|
noload => pbx_gtkconsole.so |
||||
|
;load => pbx_gtkconsole.so |
||||
|
noload => pbx_kdeconsole.so |
||||
|
; |
||||
|
; Intercom application is obsoleted by |
||||
|
; chan_oss. Don't load it. |
||||
|
; |
||||
|
noload => app_intercom.so |
||||
|
; |
||||
|
; The 'modem' channel driver and its subdrivers are |
||||
|
; obsolete, don't load them. |
||||
|
; |
||||
|
noload => chan_modem.so |
||||
|
noload => chan_modem_aopen.so |
||||
|
noload => chan_modem_bestdata.so |
||||
|
noload => chan_modem_i4l.so |
||||
|
; |
||||
|
; Comment this out (after installing CAPI middleware and hardware |
||||
|
; drivers) if you have CAPI-able hardware and wish to use it in |
||||
|
; Asterisk. |
||||
|
; |
||||
|
noload => chan_capi.so |
||||
|
; |
||||
|
load => res_musiconhold.so |
||||
|
; |
||||
|
; Do not load load local channel drivers (using the system speaker) by default, |
||||
|
; they are not used in most installations and might block the sound hardware |
||||
|
; |
||||
|
noload => chan_alsa.so |
||||
|
noload => chan_console.so |
||||
|
noload => chan_oss.so |
||||
|
; |
||||
|
; Disable CDR logging to SQLite by default since it writes unconditionally to |
||||
|
; cdr.db without a way to rotate it. |
||||
|
; |
||||
|
noload => cdr_sqlite.so |
||||
|
; |
||||
|
; These conflict with app_directory.so and each other. |
||||
|
noload => app_directory_odbc.so |
||||
|
; |
||||
|
; Enable these if you want to configure Asterisk in a database |
||||
|
; |
||||
|
noload => res_config_odbc.so |
||||
|
noload => res_config_pgsql.so |
||||
|
; |
||||
|
; Module names listed in "global" section will have symbols globally |
||||
|
; exported to modules loaded after them. |
||||
|
; |
||||
|
[global] |
@ -0,0 +1,10 @@ |
|||||
|
[system-udp] |
||||
|
type=transport |
||||
|
protocol=udp |
||||
|
bind=0.0.0.0 |
||||
|
|
||||
|
|
||||
|
[system-tcp] |
||||
|
type=transport |
||||
|
protocol=tcp |
||||
|
bind=0.0.0.0 |
@ -0,0 +1,36 @@ |
|||||
|
[base_phone](!) |
||||
|
type = wizard |
||||
|
transport = system-udp |
||||
|
accepts_registrations = yes |
||||
|
sends_registrations = no |
||||
|
accepts_auth = yes |
||||
|
sends_auth = no |
||||
|
aor/max_contacts = 1 |
||||
|
aor/remove_existing = yes |
||||
|
endpoint/allow = !all,alaw |
||||
|
endpoint/direct_media = yes |
||||
|
|
||||
|
[participant_phone](!,base_phone) |
||||
|
endpoint/context = participants |
||||
|
|
||||
|
[participant_emerg](!,base_phone) |
||||
|
endpoint/context = emerg |
||||
|
|
||||
|
[org_phone](!,base_phone) |
||||
|
endpoint/context = orgs |
||||
|
|
||||
|
[odorik] |
||||
|
type = wizard |
||||
|
transport = system-udp |
||||
|
sends_auth = yes |
||||
|
sends_registrations = yes |
||||
|
remote_hosts = 81.31.45.51 ; sip.odorik.cz |
||||
|
; public number: 910 128 976 |
||||
|
outbound_auth/username = 747515 |
||||
|
#include odorik_pass.conf |
||||
|
endpoint/context = odorik |
||||
|
aor/qualify_frequency = 15 |
||||
|
endpoint/allow = !all,alaw |
||||
|
|
||||
|
#include pjsip_wizard_phones.conf |
||||
|
|
@ -0,0 +1,6 @@ |
|||||
|
[general] |
||||
|
|
||||
|
format=wav |
||||
|
|
||||
|
[default] |
||||
|
#include voicemail_gen.conf |
@ -0,0 +1,6 @@ |
|||||
|
interface=eth0 |
||||
|
bind-dynamic |
||||
|
dhcp-authoritative |
||||
|
listen-address=172.16.0.1 |
||||
|
dhcp-range=172.16.0.100,172.16.0.200 |
||||
|
dhcp-leasefile=/tmp/dhcp.leases |
@ -0,0 +1,4 @@ |
|||||
|
dhcp-vendorclass=set:CiscoIPPhone,"Cisco Systems, Inc. IP Phone" |
||||
|
dhcp-option=tag:CiscoIPPhone,150,0.0.0.0 |
||||
|
enable-tftp |
||||
|
tftp-root=/opt/ksp/tftp |
@ -0,0 +1,174 @@ |
|||||
|
#!/usr/bin/perl |
||||
|
|
||||
|
use strict; |
||||
|
use warnings; |
||||
|
|
||||
|
use Digest::SHA qw(hmac_sha1_hex); |
||||
|
use Encode; |
||||
|
use Text::Unidecode; |
||||
|
|
||||
|
mkdir "tftp/Phones"; |
||||
|
|
||||
|
my $fh; |
||||
|
|
||||
|
my %config; |
||||
|
open $fh, '<', 'config.txt' or die "Cannot read file config: $!\n"; |
||||
|
while (<$fh>) { |
||||
|
chomp; |
||||
|
my ($key, $value) = split /=/, $_, 2; |
||||
|
$config{$key} = $value; |
||||
|
} |
||||
|
close $fh; |
||||
|
|
||||
|
my $server_ip = $config{server_ip}; |
||||
|
my $ip_template = $server_ip; |
||||
|
$ip_template =~ s/\.[^.]*$//; |
||||
|
my $fake_second_half = $config{fake_year}; |
||||
|
|
||||
|
my $sipdefault_reflash = <<"EOD"; |
||||
|
image_version: P0S3-8-12-00 |
||||
|
phone_password: $config{telnet_pass} |
||||
|
encrypt_key: 00000000000000000000000000000000 |
||||
|
telnet_level: 2 |
||||
|
tftp_cfg_dir: "" |
||||
|
EOD |
||||
|
chomp $sipdefault_reflash; |
||||
|
|
||||
|
open my $phones_fh, '<', 'phones.txt' or die "Cannot read file phones.txt: $!\n"; |
||||
|
open my $ast_fh, '>', 'etc_asterisk/pjsip_wizard_phones.conf' or die "Cannot create file etc_asterisk/pjsip_wizard_phones.conf: $!\n"; |
||||
|
open my $dnsmasq_fh, '>', 'etc_dnsmasq.d/phones.conf' or die "Cannot create file etc_dnsmasq.d/phones.conf: $!\n"; |
||||
|
open my $directory_fh, '>', 'www/directory.txt' or die "Cannot create file www/directory.txt: $!\n"; |
||||
|
open my $voicemail_fh, '>', 'etc_asterisk/voicemail_gen.conf' or die "Cannot create file etc_asterisk/voicemail_gen.conf: $!\n"; |
||||
|
|
||||
|
print $ast_fh "; This is autogenerated file, do not edit it!\n"; |
||||
|
print $dnsmasq_fh "# This is autogenerated file, do not edit it!\n"; |
||||
|
print $directory_fh "# This is autogenerated file, do not edit it!\n"; |
||||
|
print $voicemail_fh "; This is autogenerated file, do not edit it!\n"; |
||||
|
|
||||
|
while (<$phones_fh>) { |
||||
|
chomp $_; |
||||
|
next if $_ =~ /^(?:#|$)/; |
||||
|
$_ =~ s/#.*//; |
||||
|
$_ =~ s/\s*$//; |
||||
|
|
||||
|
my ($line, $mac, $alias, $name) = split /\s+/, $_, 4; |
||||
|
die "Invalid line $.: $_\n" unless defined $name; |
||||
|
|
||||
|
$mac = uc $mac; |
||||
|
my $name_latin1 = $name; |
||||
|
Encode::from_to($name_latin1, 'UTF-8', 'ISO-8859-1', sub { unidecode(chr($_[0])) }); |
||||
|
|
||||
|
$line =~ /^[2-9][0-9]$/ or die "Invalid LINE $line on line $.: $_\n"; |
||||
|
$alias =~ /^[A-Za-z0-9_]{1,20}$/ or die "Invalid ALIAS $alias on line $.: $_\n"; |
||||
|
length $name_latin1 <= 30 or die "Too long NAME $name on line $.: $_\n"; |
||||
|
|
||||
|
my $parent = ($line =~ /^2[0-9]$/) ? 'org_phone' : 'participant_phone'; |
||||
|
my $pass = substr(hmac_sha1_hex($line, $config{hmac_key}), 0, 12); |
||||
|
|
||||
|
my $cisco_fh; |
||||
|
my $ciscofile; |
||||
|
if ($mac ne '-') { |
||||
|
$mac =~ /^(?:[0-9A-F]{2}:){5}[0-9A-F]{2}$/ or die "Invalid MAC $mac on line $.: $_\n"; |
||||
|
$ciscofile = $mac; |
||||
|
$ciscofile =~ s/://g; |
||||
|
|
||||
|
open $cisco_fh, '>', "tftp/Phones/SIP$ciscofile.cnf" or die "Cannot create file tftp/Phones/SIP$ciscofile.cnf: $!\n"; |
||||
|
print $cisco_fh <<"EOD"; |
||||
|
# This is autogenerated file, do not edit it! |
||||
|
phone_label: "$fake_second_half Klapka $line " |
||||
|
phone_prompt: "Telnet phone $line" |
||||
|
proxy_register: 1 |
||||
|
proxy1_address: $server_ip |
||||
|
proxy1_port: 5060 |
||||
|
line1_name: $line |
||||
|
line1_authname: $line |
||||
|
line1_password: $pass |
||||
|
line1_displayname: "$alias" |
||||
|
line1_shortname: "$name_latin1" |
||||
|
sntp_server: $server_ip |
||||
|
sntp_mode: unicast |
||||
|
services_url: http://$server_ip/services.xml |
||||
|
directory_url: http://$server_ip/directory.xml |
||||
|
logo_url: http://$server_ip/logo.bmp |
||||
|
messages_uri: 131 |
||||
|
telnet_level: 2 |
||||
|
EOD |
||||
|
close $fh; |
||||
|
} |
||||
|
|
||||
|
print $ast_fh <<"EOD"; |
||||
|
[$line]($parent) |
||||
|
inbound_auth/username = $line |
||||
|
inbound_auth/password = $pass |
||||
|
endpoint/mailboxes = $line |
||||
|
EOD |
||||
|
if ($parent eq 'participant_phone') { |
||||
|
print $ast_fh <<"EOD"; |
||||
|
[emerg$line](participant_emerg) |
||||
|
inbound_auth/username = emerg$line |
||||
|
inbound_auth/password = $pass |
||||
|
EOD |
||||
|
if ($mac ne '-') { |
||||
|
print $cisco_fh <<"EOD" |
||||
|
proxy2_address: $server_ip |
||||
|
proxy2_port: 5060 |
||||
|
line2_name: emerg$line |
||||
|
line2_authname: emerg$line |
||||
|
line2_password: $pass |
||||
|
line2_displayname: "Emergency $line" |
||||
|
line2_shortname: " " |
||||
|
EOD |
||||
|
} |
||||
|
|
||||
|
} else { |
||||
|
if ($mac ne '-') { |
||||
|
print $cisco_fh <<"EOD" |
||||
|
dnd_control: 0 |
||||
|
EOD |
||||
|
} |
||||
|
} |
||||
|
if ($mac ne '-') { |
||||
|
close $cisco_fh; |
||||
|
open $fh, '>', "tftp_reflash/SIP$ciscofile.cnf" or die "Cannot create file tftp_reflash/SIP$ciscofile.cnf: $!\n"; |
||||
|
print $fh <<"EOD"; |
||||
|
# This is autogenerated file, do not edit it! |
||||
|
$sipdefault_reflash |
||||
|
proxy_register: 0 |
||||
|
line1_name: $line |
||||
|
EOD |
||||
|
} |
||||
|
if ($mac ne '-') { |
||||
|
print $dnsmasq_fh <<"EOD"; |
||||
|
dhcp-host=$mac,$ip_template.$line,$alias |
||||
|
EOD |
||||
|
} |
||||
|
print $directory_fh <<"EOD"; |
||||
|
$name=$line |
||||
|
EOD |
||||
|
|
||||
|
print $voicemail_fh <<"EOD" |
||||
|
$line => 0000,$name |
||||
|
EOD |
||||
|
} |
||||
|
|
||||
|
close $phones_fh; |
||||
|
close $ast_fh; |
||||
|
close $dnsmasq_fh; |
||||
|
close $directory_fh; |
||||
|
close $voicemail_fh; |
||||
|
|
||||
|
open $fh, '>', 'tftp_reflash/SIPDefault.cnf' or die "Cannot create file tftp_reflash/SIPDefault.cnf: $!\n"; |
||||
|
print $fh <<"EOD"; |
||||
|
# This is autogenerated file, do not edit it! |
||||
|
$sipdefault_reflash; |
||||
|
EOD |
||||
|
close $fh; |
||||
|
|
||||
|
open $fh, '>', 'tftp/RINGLIST.DAT' or die "Cannot create file tftp/RINGLIST.DAT: $!\n"; |
||||
|
foreach (<tftp/RingTones/*.pcm>) { |
||||
|
$_ =~ m{^tftp/(RingTones/(.*)\.pcm)$}; |
||||
|
my ($file, $name) = ($1, $2); |
||||
|
$name =~ s/_/ /g; |
||||
|
print $fh "$name\t$file\n"; |
||||
|
} |
||||
|
close $fh; |
@ -0,0 +1,11 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
i=0 |
||||
|
grep . hr.txt | while read line; do |
||||
|
i=$((i+1)) |
||||
|
echo ">> [$i] $line" |
||||
|
fn=hr/$(printf %03d $i).wav |
||||
|
if [[ -e "$fn" ]]; then continue; fi |
||||
|
./tts.sh "$line" "$fn" |
||||
|
sleep 10 |
||||
|
done |
@ -0,0 +1,16 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
gen_sound() { |
||||
|
fn="sounds/$1.wav" |
||||
|
[[ -e "$fn" ]] || ./tts.sh "$2" "$fn" |
||||
|
} |
||||
|
gen_sound nocni_klid "Z důvodu nočního klidu budete přesměrováni do hlasové schránky. Pokud chcete telefonovat v reálném čase, můžete oba zavolat do společné konference." |
||||
|
gen_sound heslo "Zadejte heslo" |
||||
|
gen_sound spatne_heslo "Špatné heslo" |
||||
|
gen_sound klapka "Zadejte číslo klapky" |
||||
|
gen_sound wc_thanks "Děkujeme za použití toalety. Nezapomeňte si umýt ruce." |
||||
|
gen_sound wc_thanks_m "Děkujeme, že jste použil naše toalety. Nezapomeňte si umýt ruce." |
||||
|
gen_sound wc_thanks_f "Děkujeme, že jste použila naše toalety. Nezapomeňte si umýt ruce." |
||||
|
gen_sound tp_prizemi "V kontaminační komoře na nulté palubě došel toaletní papír. Prosíme cestující, aby se solidárně podělili o své noviny." |
||||
|
gen_sound tp_prvni "V kontaminační komoře na první palubě došel toaletní papír. Prosíme cestující, aby se solidárně podělili o své noviny." |
||||
|
gen_sound tp_druhe "V kontaminační komoře na druhé palubě došel toaletní papír. Prosíme cestující, aby se solidárně podělili o své noviny." |
@ -0,0 +1,12 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
echo "Action: login |
||||
|
username: admin |
||||
|
secret: admin |
||||
|
events: off |
||||
|
|
||||
|
Action: hangup |
||||
|
Channel: /.*/ |
||||
|
" | socat - TCP:localhost:5038 |
||||
|
|
||||
|
|
@ -0,0 +1,179 @@ |
|||||
|
VŠEOBECNÉ SMĚRNICE PROVOZU LODI |
||||
|
|
||||
|
Pokud je vaše pracovní uniforma kontaminována dihydrogen monoxidem, použijte vysokokapacitní savou substanci pro odstranění kontaminace. |
||||
|
|
||||
|
Loď je vybavena telekomunikačním systémem, jehož terminály jsou rozmístěny ve většině obytných i jiných prostor. |
||||
|
Tyto terminály smíte využívat pro vzájemnou komunikaci s posádkou i s vedením lodi. |
||||
|
Váš hovor může být monitorován pro zlepšení služeb, které jsou k dispozici vedení lodi. |
||||
|
Zároveň budou terminály využívány pro svolávání posádky či vyvolání poplachu. |
||||
|
Tyto terminály je ZAKÁZÁNO ničit, vypojovat, poškozovat či jinak s nimi nemístně manipulovat. |
||||
|
|
||||
|
V případě katastrofálního nedostatku toaletního papíru, který je detekován až po zahájení využívání toalety, použijte pro přivolání asistence přiloženého telekomunikačního zařízení. |
||||
|
|
||||
|
Strava na lodi je vydávána nejméně třikrát denně (snídaně, oběd, večeře). |
||||
|
Pro blaho posádky je povinnná účast na snídani. |
||||
|
Snídani předchází dobrovolná tělesná rozcvička a preventivní test psychoakustické zdatnosti. |
||||
|
Podmínkou účasti na snídani je účast na rozcvičce. |
||||
|
|
||||
|
Vzdělávání posádky je vedením podporováno. |
||||
|
Z tohoto důvodu se ve společenských prostorách budou každý den pořádat přibližně tři bloky odborného trénování a lekcí z teorie civilizace a vesmírné kolonizace. |
||||
|
Na těchto lekcích je přísně zakázáno rušit či spát. |
||||
|
Spící osoby budou kosmeticky či geneticky modifikovány. |
||||
|
|
||||
|
Při rekreační rotační pohybové hře kruhozávodu po směru hodinových ručiček budou libovolné vzpoury tvrdě potlačeny. |
||||
|
Viníci budou vyhozeni přetlakovou komorou do mezihvězdného prostoru, následně budou opět zachyceni a zpracováni na karbonovou pastu. |
||||
|
|
||||
|
Vedení by chtělo důrazně varovat posádku lodi o faktu, že kdo umře v Polsku, umře i ve skutečnosti. |
||||
|
|
||||
|
Je zakázáno chovat na lodi domácí mazlíčky či jinou zvěř mimo prostor skladiště biologického materiálu. |
||||
|
Vyjímku tvoří lišky, hroši, prasata a medvědi. |
||||
|
|
||||
|
Každý lodní den bude vyhrazeno nejméně třicet tři procent dne na spánek či odpočinek. |
||||
|
Definice lodního dne, spánku, odpočinku a procent bude upřesněna. |
||||
|
|
||||
|
Při zjištění incidentu zcizení vlastního předmětu jiným členem posádky je nutno zajistit znalost jména všech zúčastněných osob. |
||||
|
|
||||
|
V případě závady na skafandru je možno vyžádat si od vedení lodi náhradní. |
||||
|
Mějte ovšem na paměti, že nadbytečných skafandrů je omezené množství. |
||||
|
|
||||
|
K respirátorům jsou k dispozici speciální kyslíkové náplně s vůní mrkve. |
||||
|
|
||||
|
Je přísně zakázáno krmit zvěř ve skladišti biologického materiálu. |
||||
|
|
||||
|
Po večerce se uložte ke spánku v gravitačních kójích. |
||||
|
Pro kvalitní spánek je nutné nejdříve ke svému jazyku připojit kabely s koncovkou typu krokodýl, která stimuluje sny, detekuje náměsíčnost a slouží jako efektivní budíček. |
||||
|
Budíček smí využívat pouze bezpečných úrovní napětí. |
||||
|
|
||||
|
Pokud nastane katastrofální selhání štěpného reaktoru, použijte k pacifikaci zběhlých neutronů vystužených kontrolních tyčí z boronu. |
||||
|
|
||||
|
Vedení lodi by chtělo zvlášť poděkovat umělci Markovi "Maark" Černému za design lodního exteriéru. |
||||
|
|
||||
|
Pro zlepšenou orientaci posádky je interiér lodi vybaven orietačními symboly a směrovkami. |
||||
|
Mějte na paměti, že směrovky jsou orientované! Navíc je zaručeno, že graf směrovek je 2-souvislý. |
||||
|
|
||||
|
Je přísně zakázáno kontaminovat mezihvězdný prostor odpadky, jako jsou například konzervy. |
||||
|
|
||||
|
Veškerá rekreační zařízení jsou testována na dětech. |
||||
|
|
||||
|
Do stázové komory je vstup povolen pouze v pyžamu splňujícím normu 3GPP-4923587-3B. |
||||
|
Nedodržení může vyústit ve smrt stářím. |
||||
|
|
||||
|
Berte na vědomí, že červená reflexní etiketa značí extrémně pálivé pokrmy. |
||||
|
|
||||
|
Politické mapy nově kolonizovaných území musí splňovat, že sousední území nejsou obarvena shodně a jsou použity nejvýše čtyři barvy. |
||||
|
|
||||
|
Pro případ politické diskuze jsou nouzové plamenomety uloženy na třetí palubě. |
||||
|
|
||||
|
Nekrmte lodní kočku bez jejího svolení. |
||||
|
|
||||
|
Veškerá data o posádce (včetně záznamů pohybu, biotelemetrie, vyhledávaných frází a publikovaných příspěvků na lodní sociální síti) |
||||
|
budou využita pro algoritmické vylepšení a personalizaci lodních předpisů. |
||||
|
|
||||
|
Každý člen posádky musí znát nejméně 50 souhvězdí. |
||||
|
|
||||
|
|
||||
|
|
||||
|
|
||||
|
|
||||
|
POKYNY PŘI EVAKUACI |
||||
|
|
||||
|
Veškerá posádka lodi je povinna řídit se evakuačními pokyny. |
||||
|
|
||||
|
Pokud dojde k evakuaci z důvodu úniku radioaktivního materiálu ze štěpného reaktoru, |
||||
|
z důvodu vniku radioaktivního materiálu do fůzního reaktoru, |
||||
|
kvůli selhání vzduchotechniky, softwarové vyjímky, kolize s cizím objektem, |
||||
|
kolize se spřízněným objektem, nebo z důvodu napadení cizí formou života, |
||||
|
ignorujte v tomto případě všeobecné nařízení §451-3. |
||||
|
|
||||
|
Pokud dojde k evakuaci z důvodu ztráty elektrické energie, |
||||
|
z důvodu vniku radioaktivního materiálu do fůzního reaktoru, |
||||
|
kvůli prudkému poklesu tlaku, kontaminaci melounovou Kofolou či katastrofálnímu nadbytku čočky, |
||||
|
ignorujte lemma 6.66. |
||||
|
|
||||
|
Pokyny: |
||||
|
|
||||
|
Každý člen posádky je především povinen řídit se pokyny z lodní telefonní sítě. |
||||
|
S telefony je přísně zakázáno neoprávněně manipulovat či narušovat jejich činnost. |
||||
|
|
||||
|
Každý člen posádky je povinen řídit se pokyny velících důstojníků, a to i mimo své domovské oddělení. |
||||
|
|
||||
|
Evakuace je zahájena všeobecným poplachem. |
||||
|
|
||||
|
Po zahájení evakuace se urychleně připravte opustit loď. |
||||
|
Očekávaná doba na přípravu je PĚT AŽ SEDM MINUT. |
||||
|
Pomalejší členové posádky budou zanecháni na lodi! |
||||
|
|
||||
|
S sebou si vemte: |
||||
|
nezbytnou osobní výbavu na 2 až 5 hodin v mezihvězdném prostoru, |
||||
|
vhodný exosuit do slunečního větru, meteorického deště a zimy blízké absolutní nule, |
||||
|
osobní jetpack, |
||||
|
otvírák na konzervy a lžičku, |
||||
|
diplomatickou příručku, |
||||
|
šifrovací pomůcky |
||||
|
kyanidovou tabletku. |
||||
|
|
||||
|
Po shromáždění osobní výbavy se urychleně přesuňte k přetlakové komoře. |
||||
|
|
||||
|
Zde vám bude vydán skafandr, který si nasaďte před opuštěním lodi. |
||||
|
|
||||
|
Po opuštění lodi se přesuňte k nástupnímu prostoru únikového modulu a urychleně do něj nastupte. |
||||
|
|
||||
|
Únikový modul má kapacitu DESET osob. |
||||
|
|
||||
|
Do únikového modulu vkročte PRAVOU nohou. |
||||
|
|
||||
|
Unikový modul odlétá do PATNÁCTI minut od zahájení evakuace a v zájmu záchrany co největší části posádky na nikoho nečeká. |
||||
|
|
||||
|
Jakmile budete v bezpečí, řiďte se pokyny pro zjistění stavu lodi a příčiny evakuace. |
||||
|
|
||||
|
|
||||
|
|
||||
|
|
||||
|
|
||||
|
POKYNY V PŘÍPADĚ KONTAKTU S CIZÍ FORMOU ŽIVOTA |
||||
|
|
||||
|
Při komunikaci ujistěte cizí formu života, že sdělené názory jsou vaše vlastní a nereprezentují oficiální stanovisko Hegemonie člověka. |
||||
|
|
||||
|
V případě nenalezení společného jazyka využijte Braillovo písmo. |
||||
|
|
||||
|
Při konfliktu s formou života na bázi stroje pamatujte, že před kyBorkem neutečete. |
||||
|
|
||||
|
|
||||
|
|
||||
|
|
||||
|
|
||||
|
POKYNY PRO POUŽÍVÁNÍ TELEKOMUNIKAČNÍCH ZAŘÍZENÍ |
||||
|
|
||||
|
Je přísně zakázáno libovolné telekomunikační zařízení vypínat, odpojovat z rozvodné sítě či jinak narušovat jeho činnost! |
||||
|
|
||||
|
Dále je zakázáno měnit nastavení libovolného terminálu. |
||||
|
Při problémech se obraťte na vedení posádky či lodního síťaře. |
||||
|
|
||||
|
Nenechávejte vyvěšené sluchátko! |
||||
|
|
||||
|
V případě vypojení libovolného kabelu z terminálu DBEJTE ZVÝŠENÉ OPATRNOSTI! Terminály jsou netradičně napájeny z datových kabelů napětím 48V. |
||||
|
|
||||
|
Je zakázáno olizovat libovolné dráty. |
||||
|
Některé jsou pod napětím. |
||||
|
Navíc jsou ostré. |
||||
|
|
||||
|
Terminál může být použit k účelům všeobecné distribuce informace. |
||||
|
|
||||
|
|
||||
|
|
||||
|
|
||||
|
|
||||
|
POKYNY V PŘÍPADĚ NÁVŠTĚVY EXOPLANETY |
||||
|
|
||||
|
Tyto pokyny se vztahují pouze pro návštěvy exoplanet s prokazatelnou přítomností vyšších organismů. |
||||
|
Na exoplanetách s pouze bakteriálním životem či zcela bez biosféry se řiďte předpisy pro návštěvu asteroidů vyjma sekce 3 pokynů pro chování v mikrogravitaci. |
||||
|
|
||||
|
Při pohybu na exoplanetách dbejte zvýšené opatrnosti. |
||||
|
|
||||
|
Všichni členové posádky jsou povinni pohybovat se ve skupinách nejméně dvou osob. |
||||
|
|
||||
|
V případě výskytu inteligentního domorodého života omezte kontakt na minimum, není-li vedením lodi specifikováno jinak. |
||||
|
|
||||
|
Je doporučeno zahrnout do výbavy expedice šifrovací pomůcky. |
||||
|
|
||||
|
Každá skupina je povinna mít s sebou nejméně jeden měřič ionizujícího záření. |
@ -0,0 +1,5 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
printf "file '%s'\n" hr/*.wav > hr_concat.txt |
||||
|
ffmpeg -f concat -safe 0 -i hr_concat.txt -c copy sounds/hr.wav |
||||
|
|
@ -0,0 +1,6 @@ |
|||||
|
#!/bin/sh |
||||
|
pass=`sed -n 's/telnet_pass=//p' config.txt` |
||||
|
ip=`sed -n 's/server_ip=//p' config.txt | sed 's/\.[0-9]*$//'` |
||||
|
for i in `cat phones.txt | grep -v backup | grep -v \- | sed -n 's/^\([0-9][0-9]\).*/\1/p'`; do |
||||
|
admin_scripts/list_errors.pl "$ip.$i" "$pass" 2>&1 | sed '/^$/d' | sed "s/^/$i: /" |
||||
|
done |
@ -0,0 +1 @@ |
|||||
|
*/10 * * * * cd /opt/ksp; ./list_errors.sh | sed -E 's/172\.16\.0\.//;s/,? ?port 23//;s/ ?at .* line [0-9]*//' > /tmp/error.log.new; mv /tmp/error.log.new /tmp/error.log |
@ -0,0 +1,54 @@ |
|||||
|
#!/bin/bash -eu |
||||
|
|
||||
|
usage() { |
||||
|
echo >&2 "usage: $0 <input> <output>" |
||||
|
exit 1 |
||||
|
} |
||||
|
|
||||
|
[[ $# == 2 ]] || usage |
||||
|
FW_INFILE="$1" |
||||
|
FW_OUTFILE="$2" |
||||
|
|
||||
|
MIME=`file -b --mime-type "$FW_INFILE"` |
||||
|
|
||||
|
case $MIME in |
||||
|
image/gif) |
||||
|
giftopnm "$FW_INFILE" > "$FW_OUTFILE" 2>/dev/null |
||||
|
;; |
||||
|
image/jpeg |\ |
||||
|
image/jpg) |
||||
|
jpegtopnm "$FW_INFILE" > "$FW_OUTFILE" 2>/dev/null |
||||
|
;; |
||||
|
image/png) |
||||
|
pngtopnm "$FW_INFILE" > "$FW_OUTFILE" 2>/dev/null |
||||
|
;; |
||||
|
image/x-ms-bmp |\ |
||||
|
image/bmp |\ |
||||
|
image/x-bmp |\ |
||||
|
image/x-bitmap |\ |
||||
|
image/x-xbitmap |\ |
||||
|
image/x-win-bitmap |\ |
||||
|
image/x-windows-bmp |\ |
||||
|
image/ms-bmp) |
||||
|
bmptoppm "$FW_INFILE" > "$FW_OUTFILE" 2>/dev/null |
||||
|
;; |
||||
|
*) |
||||
|
echo "Unknown file contents. [$MIME]" >&2 |
||||
|
exit 1 |
||||
|
;; |
||||
|
esac |
||||
|
|
||||
|
MIME2=`file -b --mime-type "$FW_OUTFILE"` |
||||
|
case $MIME2 in |
||||
|
image/x-portable-pixmap |\ |
||||
|
image/x-portable-bitmap |\ |
||||
|
image/x-portable-greymap) |
||||
|
#temporary file created |
||||
|
;; |
||||
|
*) |
||||
|
echo "Failed to convert file. [$MIME => $MIME2]" >&2 |
||||
|
exit 1 |
||||
|
;; |
||||
|
esac |
||||
|
|
||||
|
exit 0 |
After Width: | Height: | Size: 6.1 KiB |
After Width: | Height: | Size: 797 B |
After Width: | Height: | Size: 6.1 KiB |
After Width: | Height: | Size: 777 B |
After Width: | Height: | Size: 6.1 KiB |
After Width: | Height: | Size: 6.1 KiB |
@ -0,0 +1,55 @@ |
|||||
|
#!/bin/bash |
||||
|
set -eu |
||||
|
|
||||
|
CONVERTED_FILE=processed.pnm |
||||
|
FW_INFILE="$1" |
||||
|
TARGET="$2" |
||||
|
./anytoppm.sh "$FW_INFILE" $CONVERTED_FILE || exit 1 |
||||
|
|
||||
|
#generate logo for the phone |
||||
|
PREVIEW=_preview.png |
||||
|
FW_IDENT=logo_sip |
||||
|
|
||||
|
case $FW_IDENT in |
||||
|
logo_sip) |
||||
|
# BMP 90x56 (8-bit), phone can display 4 colors |
||||
|
{ cat $CONVERTED_FILE | pnmscale -width 90 -height 56 | ppmquant 4 | ./ppmfix.sh | ppmtobmp -bpp=8 > $TARGET; } 2>/dev/null |
||||
|
|
||||
|
#generate logo preview for Operator's Administration |
||||
|
{ cat $TARGET | bmptopnm | ./ppmfix.sh | pnmtopng > $PREVIEW; } 2>/dev/null |
||||
|
;; |
||||
|
logo_sep_bw) |
||||
|
# PNG 320x196 (8-bit), phone can display a 4 color PNG file |
||||
|
{ cat $CONVERTED_FILE | pnmscale -width 320 -height 196 | ppmquant 4 | ./ppmfix.sh | pnmtopng > $TARGET; } 2>/dev/null |
||||
|
# BMP 80x49 (8-bit), phone can display a 4 color PNG file |
||||
|
{ cat $CONVERTED_FILE | pnmscale -width 80 -height 49 | ppmquant 4 | ./ppmfix.sh | pnmtopng > $TARGET_TN; } 2>/dev/null |
||||
|
|
||||
|
#generate logo preview for Operator's Administration |
||||
|
cp $TARGET $PREVIEW |
||||
|
;; |
||||
|
logo_sep_color) |
||||
|
# PNG 320x212 (12-bit) |
||||
|
{ cat $CONVERTED_FILE | pnmscale -width 320 -height 212 | ppmquant 4096 | ./ppmfix.sh | pnmtopng > $TARGET; } 2>/dev/null |
||||
|
# PNG 80x53 (12-bit) |
||||
|
{ cat $CONVERTED_FILE | pnmscale -width 80 -height 53 | ppmquant 4096 | ./ppmfix.sh | pnmtopng > $TARGET_TN; } 2>/dev/null |
||||
|
|
||||
|
#generate logo preview for Operator's Administration |
||||
|
cp $TARGET $PREVIEW |
||||
|
;; |
||||
|
logo_sep_color_16) |
||||
|
# PNG 320x212 (16-bit) |
||||
|
{ cat $CONVERTED_FILE | pnmscale -width 320 -height 212 | ppmquant 65536 | ./ppmfix.sh | pnmtopng > $TARGET; } 2>/dev/null |
||||
|
# PNG 80x53 (16-bit) |
||||
|
{ cat $CONVERTED_FILE | pnmscale -width 80 -height 53 | ppmquant 65536 | ./ppmfix.sh | pnmtopng > $TARGET_TN; } 2>/dev/null |
||||
|
|
||||
|
#generate logo preview for Operator's Administration |
||||
|
cp $TARGET $PREVIEW |
||||
|
;; |
||||
|
*) |
||||
|
echo "Unknown logo ident. [$FW_IDENT]" >&2 |
||||
|
exit 1 |
||||
|
;; |
||||
|
esac |
||||
|
|
||||
|
|
||||
|
|
@ -0,0 +1,21 @@ |
|||||
|
#!/usr/bin/gawk -f |
||||
|
|
||||
|
BEGIN { |
||||
|
fix = 0 |
||||
|
} |
||||
|
|
||||
|
NR == 3 && /^0$/ { |
||||
|
fix = 1 |
||||
|
print "1" |
||||
|
next |
||||
|
} |
||||
|
|
||||
|
fix == 0 { |
||||
|
print |
||||
|
next |
||||
|
} |
||||
|
|
||||
|
fix == 1 { |
||||
|
gsub(/\x00/, "\x01", $0) |
||||
|
print $0 |
||||
|
} |
@ -0,0 +1,58 @@ |
|||||
|
#!/usr/bin/perl |
||||
|
|
||||
|
use strict; |
||||
|
use warnings; |
||||
|
|
||||
|
use DBI; |
||||
|
use Encode; |
||||
|
use Net::SIP; |
||||
|
use Net::SIP::Util qw(sip_hdrval2parts sip_uri2parts); |
||||
|
|
||||
|
my $addr = $ARGV[0]; |
||||
|
my $port = $ARGV[1]; |
||||
|
my $dbfile = $ARGV[2]; |
||||
|
|
||||
|
die "Usage: $0 listen_address listen_port database_file\n" unless $addr and $port and $dbfile; |
||||
|
|
||||
|
my $dbh = DBI->connect("DBI:SQLite:$dbfile", undef, undef, { PrintError => 0, RaiseError => 1, sqlite_unicode => 1 }); |
||||
|
|
||||
|
my $leg = Net::SIP::Leg->new(proto => 'udp', addr => $addr, port => $port) or die "Error: Cannot create leg: $!\n"; |
||||
|
my $ua = Net::SIP::Simple->new(from => '', leg => $leg) or die "Error: Cannot create user agent: $!\n"; |
||||
|
|
||||
|
$dbh->do('CREATE TABLE IF NOT EXISTS messages(id INTEGER PRIMARY KEY AUTOINCREMENT, r INT NOT NULL DEFAULT 0, f TEXT NOT NULL, t TEXT NOT NULL, m TEXT NOT NULL)'); |
||||
|
$dbh->do('CREATE INDEX IF NOT EXISTS idx ON messages(r, t)'); |
||||
|
|
||||
|
$ua->{endpoint}->set_application(sub { |
||||
|
my ($endpoint, $ctx, $packet, $leg, $from_addr) = @_; |
||||
|
|
||||
|
return unless $packet->is_request; |
||||
|
|
||||
|
my $resp; |
||||
|
if ($packet->method eq 'MESSAGE') { |
||||
|
my (undef, $for, undef, $message) = $packet->as_parts; |
||||
|
$message = decode('UTF-8', $message); |
||||
|
my $for_user = (sip_uri2parts($for))[1]; |
||||
|
my ($from) = $packet->get_header('from'); |
||||
|
($from) = sip_hdrval2parts(from => $from); |
||||
|
|
||||
|
print "Recevied message for user $for_user from uri: $from\n"; |
||||
|
|
||||
|
my $success = eval { $dbh->do('INSERT INTO messages(f, t, m) VALUES(?, ?, ?)', undef, $from, $for_user, $message) }; |
||||
|
|
||||
|
if ($success) { |
||||
|
$resp = $packet->create_response('200', 'OK'); |
||||
|
} else { |
||||
|
$resp = $packet->create_response('500', $dbh->errstr); |
||||
|
} |
||||
|
} elsif ($packet->method eq 'OPTIONS') { |
||||
|
$resp = $packet->create_response('200', 'OK'); |
||||
|
} else { |
||||
|
$resp = $packet->create_response('606', 'Not Acceptable'); |
||||
|
} |
||||
|
|
||||
|
$resp->set_header('Allow' => 'OPTIONS, MESSAGE'); |
||||
|
$endpoint->new_response($ctx, $resp, $leg, $from_addr); |
||||
|
$endpoint->close_context($ctx); |
||||
|
}); |
||||
|
|
||||
|
$ua->loop(); |
@ -0,0 +1,4 @@ |
|||||
|
[Service] |
||||
|
ExecStart=/usr/bin/perl /opt/ksp/message_receiver.pl 172.16.0.1 5062 /tmp/messages.db |
||||
|
[Install] |
||||
|
WantedBy=multi-user.target |
@ -0,0 +1,12 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
vol=9 |
||||
|
|
||||
|
|
||||
|
cd /opt/ksp |
||||
|
. config.txt |
||||
|
ip_prefix=${server_ip%.*} |
||||
|
./hangup_all.sh |
||||
|
sleep 1 |
||||
|
cat phones.txt | awk '{print $1}' | grep '^[2-5]' | xargs -i -n1 -P0 ./admin_scripts/normalize_volume.pl "$ip_prefix.{}" "$telnet_pass" "$vol" |
||||
|
|
@ -0,0 +1,40 @@ |
|||||
|
# LINE MAC ALIAS NAME |
||||
|
|
||||
|
# org |
||||
|
21 00:0c:85:b9:8d:72 org1 Org 1 |
||||
|
22 00:0a:41:9e:70:4c org2 Org 2 |
||||
|
23 00:1d:a2:66:e1:1b org3 Org 3 |
||||
|
24 00:1e:be:90:7a:1a org4 Org 4 |
||||
|
25 - lodni_kocka Lodní kočka # Medvěd |
||||
|
|
||||
|
# non-org |
||||
|
31 00:0a:8a:2c:8c:d2 prechod_komora Přechodová komora # botnik |
||||
|
32 00:0c:85:b9:8d:47 kontam_komora_0 Kontaminační komora 0 # wc přízemí |
||||
|
33 00:1b:d4:60:6e:3f lodni_kaple_1 Lodní kaple 1 # jedalen1 |
||||
|
34 00:1d:a2:66:e1:0b lodni_kaple_2 Lodní kaple 2 # jedalen2 |
||||
|
35 00:0c:85:b9:8d:57 unikovy_vychod Únikový východ # chodba |
||||
|
36 00:0a:41:f9:77:32 xenobio_lab_1 Xenobiologická laboratoř 1 # jedalen1 mala |
||||
|
37 00:1e:f7:c2:28:66 xenobio_lab_2 Xenobiologická laboratoř 2 # jedalen2 mala |
||||
|
38 00:0c:85:b9:8d:50 odd_inkub_techn Oddělení inkubačních techn. # izba 6.c |
||||
|
39 00:0c:85:b9:8a:63 odd_appl_noem Oddělení aplikované noematiky # izba 5 |
||||
|
40 00:17:0e:c8:52:bf chodba_0 Chodba 0 # chodba |
||||
|
41 00:1d:a2:66:e0:cc odd_rela_efekt Oddělení relat. efektů # izba 4 |
||||
|
42 00:1b:d4:5f:f3:33 odd_auto_agrik Oddělení autonomní agrikultury # izba 3 |
||||
|
43 00:0c:85:3b:ba:84 dekontam_sprcha Dekontaminační sprcha # sprchy |
||||
|
44 00:0c:85:b9:8d:5e kontam_komora_1 Kontaminační komora 1 # wc 1. patro |
||||
|
45 00:0a:8a:2c:8d:73 odd_civil_vycvik Oddělení civilizačního výcviku # izba 7 |
||||
|
46 00:1e:be:90:79:ea odd_psycho Oddělení psychoakustiky # izba 8 |
||||
|
47 00:0a:8a:21:57:38 serverovna Serverovna # switch |
||||
|
48 00:0c:85:48:c9:c3 sklad_nebez_odpad Sklad nebezpečného odpadu # schody |
||||
|
49 00:0c:85:8d:18:2d chodba_1 Chodba 1 # chodba |
||||
|
50 00:17:0e:c8:50:d2 odd_abstr_umeni Oddělení abstraktního umění # izba 1 |
||||
|
51 00:0c:85:8d:16:13 odd_dezinfo Oddělení dezinformace # izba 2 |
||||
|
|
||||
|
56 00:0a:8a:21:51:bc backup1 backup1 |
||||
|
57 00:0a:8a:66:49:8e backup2 backup2 |
||||
|
58 00:0a:8a:2c:8d:0b backup3 backup3 |
||||
|
59 00:0a:41:f9:79:2a backup4 backup4 |
||||
|
|
||||
|
# dead |
||||
|
#00:0a:8a:2c:8f:f1 |
||||
|
#00:0a:8a:2c:8d:74 |
@ -0,0 +1,20 @@ |
|||||
|
#!/usr/bin/python3 |
||||
|
|
||||
|
import xml.etree.ElementTree as ET |
||||
|
from datetime import datetime as dt |
||||
|
from urllib import request |
||||
|
|
||||
|
xml = request.urlopen('https://www.yr.no/place/Czech_Republic/Olomouc/Ruda_nad_Moravou/forecast.xml').read() |
||||
|
|
||||
|
root = ET.fromstring(xml) |
||||
|
days = ['Mo', 'Tu', 'We', 'Th', 'Fr', 'Sa', 'Su'] |
||||
|
|
||||
|
for time in root.iter('time'): |
||||
|
attrib = time.attrib |
||||
|
time_from = dt.strptime(attrib['from'], '%Y-%m-%dT%H:%M:%S') |
||||
|
time_to = dt.strptime(attrib['to'], '%Y-%m-%dT%H:%M:%S') |
||||
|
style = time.find('symbol').attrib |
||||
|
temperature = time.find('temperature').attrib |
||||
|
preci = time.find('precipitation') |
||||
|
output = days[time_from.weekday()] + time_from.strftime(' %H') + '-' + time_to.strftime("%Hh") + ': ' + temperature['value'] + '°C' + ', ' + style['name'] |
||||
|
print(output.replace('Partly', 'Pt.')) |
@ -0,0 +1,7 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
cd "$(dirname "$0")" |
||||
|
myself="$1" |
||||
|
[[ -n "$myself" ]] || myself=xxx |
||||
|
cat phones.txt | grep -E '^[3-5]' | cut -d' ' -f1 | grep -vFx "$myself" | sort -R | head -n 1 |
||||
|
|
@ -0,0 +1,17 @@ |
|||||
|
<DIALTEMPLATE> |
||||
|
<TEMPLATE MATCH="2." TIMEOUT="0"/> |
||||
|
<TEMPLATE MATCH="3." TIMEOUT="0"/> |
||||
|
<TEMPLATE MATCH="40" TIMEOUT="0"/> |
||||
|
<TEMPLATE MATCH="41" TIMEOUT="0"/> |
||||
|
<TEMPLATE MATCH="42" TIMEOUT="0"/> |
||||
|
<TEMPLATE MATCH="43" TIMEOUT="0"/> |
||||
|
<TEMPLATE MATCH="4445" TIMEOUT="0"/> |
||||
|
<TEMPLATE MATCH="45" TIMEOUT="0"/> |
||||
|
<TEMPLATE MATCH="46" TIMEOUT="0"/> |
||||
|
<TEMPLATE MATCH="47" TIMEOUT="0"/> |
||||
|
<TEMPLATE MATCH="48" TIMEOUT="0"/> |
||||
|
<TEMPLATE MATCH="49" TIMEOUT="0"/> |
||||
|
<TEMPLATE MATCH="5." TIMEOUT="0"/> |
||||
|
<TEMPLATE MATCH="8888" TIMEOUT="0"/> |
||||
|
<TEMPLATE MATCH="*" TIMEOUT="9999"/> |
||||
|
</DIALTEMPLATE> |
@ -0,0 +1,9 @@ |
|||||
|
џџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџ________џ________________џџџџџ___________JR__пR!'8ЛЪ���ЁЂЏЇЪ5J�������В-!-",>ЪОЄ8ЄЪ��DЊ8Џ�,*џЪ_ JJ8����;Ъ$���2"�Л5Љ�������
2�����Њ/->J*ЁФ'ЌЕ����Њ2ЌЉ>
*Ќ�)���ЁЌR
)��Ї,*_в-Џ�Љ-ЕЄ����п$ВЇФJ"пЊ�ОЏЪ"�ЅЌџ
И������в2Ф
�����ЊЏ,$"
)->8Џ�Ъ8вJ��--ЕЉВО2/RИDФ5J����Ъ"%'2Ќ��ФФв%'Є*5���ЁЌвФ! |
||||
|
/ЪЁЅ����RФЕ/*Ъ8*!Ё��в���пЪ/в������Ф8
_Є��Ъ8_2Л�ЏJЅJ>���5Ъ$)ЂЂ�ЇЕ-ЪЄ�,DЁЄЕ;/*_Е������ЌЛ Л�����ЄЇЛЛ8%,$
!JџОЄ��вЅ�ЊпJ!5 RО'Ъ����џ5*$>���ЇЪп>'R_>ЄЅ���Ђ!%"
8ФФ_Фв����ЛВИЊ�R''�������ЉЌп
D�����ЄИD2')-ВВD;ФЅ�ВJ�ЏИ_)'Фп,$*����ЪJ5в����ФвJ)_$/Є�����*%
)_џпЕВ��Ђ�ОИЛЕЅJ''�������ЉЌп
D�����ЂЛ>-%-%DЂЊ>2џЊ�Њ/ВЏџ%);Е_>$Њ���ЛвR5�Ё��ИФџџ,$Є�����п$% |
||||
|
)2В����ЌЊвRЪ$;8-"
'����Ђ���вD>
/������Ђ_2Љ��ЄЕJ!8ИЏ*$џЪЛ";Њ�ЇJJ5->8ЇЉЛ_*8Е�ЂВВ��ЌЪ
8J������ЁФ%
|
||||
|
Џ�����Њ_Jџ$%%_Rв���Ѕ��ЄЛџ/$
5_2џџЄ����ИDJЂ��ЄИФ>"*J5"/_п����В),2%5Фџвв��Ї��ФDЛОЛR |
||||
|
R��������ЕDџ������Є-5"!DDЉџRR�ЁЛВЏЏЌD$%$!,Ев8,ЏЁ�ЊЇJ*-ОЇЂ��ЏВR,ФЅ�����О5*
*ИЄ����ЇЕВџ2"_5
$��������ФЛ28О������;*"*Џ���В;*џВ5RRJЛ5,RЌЇЏЏОR/*"JЪRЛD-%>ЏЄ�ЊЕЄ�2)пЄ������Џ$ОЄ����ЇЊЕJ,!5%%-'ВЂЊЅ��Ё�ЪФп*,2вв>Љ��Ё�ВJ-,Ф��ЂЕЏ2'");,,JФЌ���RвR'$>5-5ЛЏЏЉ�ЁЏЕОЛВJ*2'пЁ�����ЄЌ>/Є�����ЏЪ5,,!//RЛвФВВИџпФп;'2,)вЕЪ8;ОЕппОЏD)2ЪИЉ�ЅЊФ'$'%;ОЂ����О_J*%$;в���ЄЅЌЕЪ-8;5/!,ИЄЂЁ���ЌФЪ;%!,ЛЊЂЅЂ�Єп>;5'/џВ�ЅЕ_8џ>85JпJ;5RФЕЌЏЕЕв;-,2;>8J52DЪЄЉЏВЏИ_/''DЕ����ЄЅО;%),5вЉ���ЇЏЕв-)5--)*//DЪЛОИЏЌЌОввџ;)"'8пџJRвЕОЕВИОD-*)';ОЉЁЉЏИJ2*$/228D_ЪЄЁЏФООџ,!%-)$8пОЌЉЉЛЛФвџDD>*)_ВЂЁЅЇЊЛJ5-*%!2ЪВЌЄЁЂЊФR>5-$'/5_ИООвџвЛФЪФОЪ>;;-8RЛЕЪD;џ_5DЪОв>;>JвФОЕВЛЕп/-,*,,;JФЌЉЉЇЊЛЪп>;,"!$)*JЕЅЂЇЉВИв55>;;5,*,5JвЛВВЊЊЪвпJ5,/5;>JпФФвЛВОпJ;2,*'5џИЌЏВФвп;;DDD;5-2;_ЪОЕЕЏЏпџџJ8258;;DџЪЪпЛЏИЪџR;/,'/DвВЕИппџDDJRRD>2;RпФОИИЛв>8;88>___пФЕЕЛпЪФџR>82*,-;RвВЊЊЛИИвJ8RR;,)-28пВЅЊЏЛЪ>25588D>JJџЪпЪФпЪџR_RJ;5;џФвЪ_ЪЪ_ппФв_RDD55JЪВЕИЛпJ52888;џџпЪОВЪџпв_8-2822DџОЕВЊЕвJJ;>;>D882;RЪИЏЌВЛЪ_R>5;;;,,5JпвИЏЌЏЪпџ>/-28>DпИОЪџџЪDDR_JDJ_џRпИВИ_Rџ;//8JR_Jџ>%-8ЛВВЂ��ВЕпФЪ2-;ФJЏЁ��Џ8*58пЌОпЊ���Ќ/)_RJ)ЏЇ�����$'%��Ђ����џ''*)RR2п/$џ�����Ќ%!%џЕ��Ё�ЇЊЊ!%-*"ЕЏИЉDJ5_�ЇЏ_5ЉЊ*">ЏЊ"!-%58ВЇвЕЊв'џФЅЊ%ИИR);п-п_ВЉ��Џ>5>;!*2Ђ����ЕОJЪJ,*џ,!5џпВ_ЪЏппОЌ_-52,/ЏЊ;8О�ЂЏЁЪ2*'J2"J��Ѕ_DЛ;%)џJ)DОЕЏ��Ъ$">*'D_пЪЛФ��Ѕ�J/ИИФ*!_�������ЪD-Ё�����Єџ)8'')!Џ�ЉИ*RЂЉRJОџИD*)*џЪФЛ5/ФЉЇЌЌЪЪ;)џФЂЏОФВD2'>)/Є���ЏЏЛ8'",5J����ЪЏ_,>п"!п��ЏЁ���Ќџ''*�Ђ����ЅD)/$!џпЇЅџп;,RЊЪD_ИЌ_'DвЁИ%2;,'Rџ;џJЪџ"8Л��ОВ�Ќвп,8Ф�����ЉЉВ"/И����ЇЌЏЅR"5,%'>DОЌЂ�Љ��ЊЛ--*џЪвпВ�Ђ��ЏJ)%,*Љ��ЇвЛџ-%$*--)DпЪЉЁ�Љ8)58-*_;5RRЌЄ��ЏЛИЅВв)'Ф������ЁЌО*,Ђ�����ЄЛв8!%")ИЄФRџФ�ЉВЌЕJ$"%)пџџR8ЊЂЇЌЪИD"%>ЇЂ��ООЕ>%%)И�����Е>2)!"/пЂ����ВИЛФR;2Л�������ИRD
;Љ������И;/!!JЕЉЇЇЪ>RЕЕ>џпИФ*'_ВОвJJ>/пп_вџRџ)!,џЕЌЊЂЉЇФ5,,������ЊR-Њ�����ЊЉВ>/5/%)*>ЕЌЇЅ���ЊпR,)DФЛЉ���ЄО;'JЏ��ЄЊИ;$"%!!);ЏЅ���ЏЪЛп2)*2,"!8>пЉЊЉ���ВJ;%
)RВЉ�����ВJ,,џЅ�ЅЌВЛ>,,/2*5>RИЉ��Їџ>џ>*$"8;5/5ЪЕЏЇЄЏВЉЉп-)
DЊ������ЁФ'
%И������О82)"")џОФџџЄЉЉЊЌЛD)"'JпЪJџВЉВЕОв"'RВЉ�ЄЌЊЕJ!'8вЂ����Ќв_5%,DЏ���ЄЉЊЉЛџп2*;ЕЅ�����ЕR%)џЇ�����Ќв;-$"8џЕЊЌЪ>џЪRџџОФD-/џвЪФЪвџпRDRRJD>2)5DЛЅЊЌЉЄЌФR/!/вЂ�����Їџ-"'>Л����ЁЉЪ88/$!$$JИЕЊ����ЏЛп5%;џџИЅЉЇЂЏОJ*$!"*JИЉЏЕЌп;>-/;5;RRџЛЉЂпФпJ>')2/%*>џЛВЉЅЉЊЌЏЕ_55*/вЊ����ЄЉО2'"*пВЅ���ЁЌОџ;/%!)_ЪЪФЛЏЉЌЌЛп>,-$-DФЛввЕЕОвпЪD*%)/RОЇЌВИ>*"%'");вВЅЁ��ЛвD8)!!!%2ЪЉЄЄЄЇЇЌЛпJ5,%!5ЪЕЇ���ЂИџ/!/џИЌЇ�ЁЪR>-$!'/>ЪЕЕЪџпЪџJпЪвD28J_вввОФФЪџJD;;>2/5JОВВЌЏО_;)*RЏЄЄЄЁЁЇИJ;8)",JЏЅЄЅЉЉЪ_J8/)),,-8RпОВЇЄЌЕЛвJ-$$*8JџпФИИВЏИОR8/,,/>пЛЕВЕФ_>58;>>JJJвЛЕИФФЛОџ>882*,8DпЪИЏВЏВЕОп_J5%"*;ЪЇЄЄЄЉЕвD8,%"'/DвЕЉЂЂЉВФ_D-*,*5DJ__пЪОЛОЛФЪ_JD528Dџпџ_вв_џпЪпJD>>J_вФООВЛпJ58-,2;RџЪЛВВЛОФпџD5-*,*2DЪЕЏЊЌЌВФпR>2/,))->џОВЏЊЛФп_;///2/2>пЪФЕЏВЛвв_>5-88>пОИЪЪЪпRDDJJD>RR_џвЛЛИФџ_D>88>>DDRпФФФЛОФЪ_J8---22>пЛВЕВИвRJD;-*-/5DЪЏЌЏЕџD;522558;RвЪЛООИФвп_RD;28>DRRЪЪвЪЪФвџJJD55;,'2JЕЕВЊ�ЉИЛЪЕЪ>-'5JЉ����ЕЛФR/DJRџ,"DФВD-Ќ�R��Е�ЕЪ;$-пЁЁЪ%>%!2�����*
>Љ����ВЛ52��")п���ЊD;Ђ��$;�Є���Ќ_D2),�ЉИЪD%JИ/5�Ё58R;вЇD)"п�ЂJЌЁЉ,,"-Љ����) 2���Є��ЇИ$;/
ОЊ!8Љ��ЇЛ;Њ��в28����ИЕ->ЏЌ�Ќ)>)ЊЂ"2��вJ/,5/2Џп)2��ФвЏ>%'Ъ_���/*%$џ���Ѕ��ЊИ%-,!ЏЌ''в�ЌDЅ��Ѕ;" |
||||
|
����Є�ЏЪЄ_ОЕЕО)ЛЌв/Л�Ђџ*$)DФ'$Ї���J,Є��ЂИЌ_>DЁЇЊ���Ђ)*8Ъ/2D_вО�ОЪ���Џ) Џ�������џ)
2R,25�ЪФЊФ8Ќ�ЅФ%"5В*"J���Є>,)Ф���Џ>8п''-%ЪЉВВВ��Ъ->*/џ8*%5%џ������Ѕ/ |
||||
|
2����ЂЊ�_5/2_J$ЄЕОЛОЪЏ��ЅJJ>/И����;5,Ъ���ЊD2%!*$ФЇ�ЂВ��Ф!%!!/;ЕЕ285'!ЛЅЊЅ���Ї** Ф������О',2,/Ъ��ЉЏОRЪЌЁ�И$*_D����ЌЛDЏ���_Л>-D>*"JФџЊ��џ;D2/ЪОФ-"*RЕ�����Ё;2
5�����ЁЄЪ2$
*2,Љ�ЁЂЏвЕ��Њ*$>в����ЂЅО"���ЊЪпR;Jџ!)>ЪЅЕ;ФЏ8D-'%-О��_-,ЛЕ����Ќп>
2������Џ;"!%88*Ъ��ЇЉЏRпЅ��Ъ!2Џ�����ЇЪ-
'Ѕ��ЌЅЕОЕЛ;''8ВЕ>;п_џRџ*>Џ�Ёџ>,%џЛЉЂ��ЇвR'_������п-2!)>!/ЛЊЄЇЅОЇ��Љ5 |
||||
|
$И�����ЅИ5$в��ЉЇЇО_ЛФ,,5И�џ)-8/5џ>,5И��ЄЪ/""5пЕ���ЂОRв�����В2,'%пJ/DИИОЇФЕЊ��Џ8$
,в�����Є5ИЁЌЂ�ЄОФЪ8,%JЂD*88-Rџ--DЇ��ЌџD"%-5Ф���џ;'"$)Е����Ђ_8;'$_в;5_п_ФЌЇЛЇ�Ёп'*">В����ЄЊџ)5ЕЌЊЅ�ЌЪИR5,/ЏЅФ**)%8DJ_>Е���в;)$)>Ќ��ЁИФ5"$!%"/Ї����В855*5ИRJв88пИЌФФЄ�Њџ5"*JЄ�����Ќ;'8ФЕЇ��ЇЌв_8,_ЛИ;%*)%/DRD_��ВџD/'!'$;Ї��ЊОФ;)'))8ЊЂЂ�ЄЛ_;5,;ОЛJDD8;ЪВВФЛЇ�ЏJ/!*JЄ����ЂВ8$;ФИЇ�ЁЉЏп_5-_ЛЛ8%,)'-D_DџЌ��ИџJ2*")$;Є��ЌОФD,*-,!DЊЅЇЁЅОФJ8-%DОвJD58JЛЌИЛВЉЂИ>-!-_Є����ЇФ5!%RЛИЇ�ЂФџ_52_Вв82,)',Jџ_Е��ЂО_D/$",ЪЄ�ЄИ_;2*-%$5ФЉЇЉВО_>2%%*пЕФвD58RФЕЪвЏЄЉЪ>-)!,5џЌ��ЂЂЌЪ8')%-J_ЛЉЄЇИЪФR>>џЪ_;2-)-;JRЪЌ�ЂВФџJ5'$$"/ЪЊЅЌЏИОп>8,)*>ОФЪИВВвJD5*)JЕВО_>;5Jв_RФЌЂвD2)!$**2џЉ��ЁЊИп22)"")8DџЕЌЌЛФОпRDRФФпJ8-''2;RИЇЁЅВФв_/*,*,5ФВИОИИ_>5-,2џвпЪОВОпџD5-;ЪИОџD;/5JR_ЪЅЉЕвD5,,5/,2вЌЉЅВЛJ;2*%'5JџЪОВЛЪпвп>DпЪЪ_D;/)-DџФВЉЉИв_8,-,*,JОЛВИЕЕпJ5-*-JџџвФЕИОвпJ2;вФФвџ_J8;JJ_ЪЏЏИЪJ>5/585->ФИЌВЕИвR82,*2>џЪОЕИЛФЪвDD_пввџR>-*5DџОЌЌЕФџ>/-/-*2RвЛЛЕЏЛв8,ФОЇ����ЅЊJ/D*JЊ��ЄВ';'*'Л�ЅЉ����ЁJЏ* )-Џ�����2;>RRИЌ��ФD�ЄЉ��Е
R�������D2%
R��Ќ),2ЊRв'D���ЇЄD>>пЂВ8%)��J-О�џJО8Ѕ�Ќ22���Ъ����J,J
$����ЇЕ�ИR5!-%;џЏ�О,ОЕ�Ѕ"JО,%$ЪИ�;8)_���Ќ8),2Њ�Є����в>/)����Е�Ї*,Љ�����Ќ>_ЁRJDО$/���DJ���Ѕ-)'8В�����Љ>)���Є%"DDпЌОвЉЕп�Ё,Ї22��ЂО)!-ЊЁЄ*J��ЂR5
)Л�������Ф, Њ���ЅВЊЛвJD)R5$'вЌЊ>��ЂФЉ�Л*,
%ЛЕ$Љ����_5"-���ЊЊЅФR2,;5$����ЉЌ)*/*>Џџ/пО��џп__ИЄ�Ъ5"%��пЉ�����Ъ-
|
||||
|
Л������Џ_$R_Љ�О)$DЛЄВ)В�ЉФ,>_вR;'*%����в2*вЁЇЄ��ЄЛ_*"����ЏЅп%*;ЪЪ���В5впЛЕ_ВЌ/џ��ЌЁ��ЁЪ)8
$>_Ђ����ЂО-Џ���Фџ,,8ФЛ$)RОџ2D��Ќ5D58Ъ_ЄЊ>2"!JЂЇИвФ��ЅЪ
,JЂ���Ё��О--�����Љпп52/D8'$/ЇвDЌИЪRЏ�ЂЊФR-пФ)>Ъ����Ф$
Е����ИО;$)!)ОЄ����_$%>)*ЪЇпRФЉЏвЕО_5Љ�ЉЌ/! в�Ї������п2
/Ѕ�����ЇФ)*')RЏИЌЌ-8DЌЊ>ОЊИ2$8,пЏв,)DЂЁЅЕИџ$>JЪЁЄ��ИR*О�����Ђ_>)%$>Є����ЏООD2)-Ов%8�ЄЏИ����ФВ2
RЉ�����Є/%'п����в/%5J!%;JЛппВ�ЂОЪ5,$!',ЊОФ5)8ВЉЛЕ��ЅJ2
п������ЂJ-�����ЕџФв,*!5Ф2$")-*ЛЊОВЅЂЁ�ЕвD>DЪJ_Ё��ЊЊп*"%_Ё��ЊИЪ-*%%,!)пЊЇ���Ъ>пJп8/JЏЊЌ��ЊввпФJ2-
5Ф������ЂЊ8
џ������пD-"%_вИ�ЏJ8ФФ_R>ИЅп5>,'ФВJ*$/�ЉИ,!)џЕЂ��ЄЏџ%п������џ**-RЛЇ��ЄвОФ_J)RВЪ;$-ЕЇЌЅ���ЄЛФ2!$2Ї���Ё�И-/8*!вЅ��ВR-,JD5;JЪвФJ_ВЕИЪвџ8!"8пЪJ>п5-вЌ�ЏџВЇЊЪ8)*JЅ����ЁЇD"!%)*ЛЂ���ЉВВџ>!-/222;>пЛИЛОФЪЕЏВЕџ/%JО8->ИЅВЊЕџ8*)$/Ё�ЇЛ5)'%*)'2ЪВЉ��ЅЪ>>8),J_;ОЏЏЊЏЕЕ_DџвОФџD'%ЪВЉ����ЇИ>)""‽Є��ЏФ;DJ,'%8џпЕЏп;>>_џ>JОЕИ_RD-DЪЕО>/5ФФRвЛв;2/;_пФЛЊЊИЛR'*%'*,/DЏ��ЄЅЏ_J;2/%$/25ОЄЁЇВЕЛО_28џR85'$-8џЛЛЕЛЊЊОЛИџ2*),2,,DвФОЉЅОЪЪ_5)!8ЪЛЕЛпJD;;5;DRОЛпЕЏЛФппJ5%!,;JџОЕФОИЕЛпDDФИЪп>>5))'-DЪЌЁЄЌЊЏп8-8/$!5џЪЅЅЕФвJ>//;__Rџџџџ_пџвЪвФФпв_D2,8пФЪџJппJRJпRD_RџJRФВЏЪв_;-,;__RRОЛФИВЕџJпџ>%%-855_ЪЕЕЉО_DJ>DD>;/28RпФВЏЊВЛФJD55;52,/JвФОИВВЛR__>//;>_пОВФпRџ_25RџџџџџпRпЕОџ88D58DџЪвџ_џџJR_ппввџRџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџ |
@ -0,0 +1,230 @@ |
|||||
|
# SIP Default Generic Configuration File |
||||
|
|
||||
|
# Image Version |
||||
|
image_version: P0S3-8-12-00 |
||||
|
|
||||
|
# Proxy Server (Can be dotted IP or FQDN) |
||||
|
proxy1_address: "" |
||||
|
proxy2_address: "" |
||||
|
proxy3_address: "" |
||||
|
proxy4_address: "" |
||||
|
proxy5_address: "" |
||||
|
proxy6_address: "" |
||||
|
|
||||
|
# Proxy Server Port (default - 5060) |
||||
|
proxy1_port: "" |
||||
|
proxy2_port: "" |
||||
|
proxy3_port: "" |
||||
|
proxy4_port: "" |
||||
|
proxy5_port: "" |
||||
|
proxy6_port: "" |
||||
|
|
||||
|
# Proxy Registration (0-disable (default), 1-enable) |
||||
|
proxy_register: 0 |
||||
|
|
||||
|
# Phone Registration Expiration [1-3932100 sec] (Default - 3600) |
||||
|
timer_register_expires: 3600 |
||||
|
|
||||
|
# Codec for media stream (g711ulaw (default), g711alaw, g729a) |
||||
|
preferred_codec: g711alaw |
||||
|
|
||||
|
# Inband DTMF Settings (0-disable, 1-enable (default)) |
||||
|
dtmf_inband: 0 |
||||
|
|
||||
|
# Out of band DTMF Settings (none-disable, avt-avt enable (default), avt_always-always avt) |
||||
|
dtmf_outofband: avt |
||||
|
|
||||
|
# DTMF dB Level Settings (1-6dB down, 2-3db down, 3-nominal (default), 4-3db up, 5-6dB up) |
||||
|
dtmf_db_level: 3 |
||||
|
|
||||
|
# SIP Timers |
||||
|
timer_t1: 500; Default 500 msec |
||||
|
timer_t2: 4000; Default 4 sec |
||||
|
sip_retx: 10; Default 10 |
||||
|
sip_invite_retx: 6; Default 6 |
||||
|
timer_invite_expires: 180; Default 180 sec |
||||
|
|
||||
|
####### New Parameters added in Release 2.0 ####### |
||||
|
|
||||
|
# Dialplan template (.xml format file relative to the TFTP root directory) |
||||
|
dial_template: Dialplan |
||||
|
|
||||
|
# TFTP Phone Specific Configuration File Directory |
||||
|
tftp_cfg_dir: Phones/; Example: ./sip_phone/ |
||||
|
|
||||
|
# Time Server (There are multiple values and configurations refer to Admin Guide for Specifics) |
||||
|
sntp_server: ""; SNTP Server IP Address |
||||
|
sntp_mode: unicast; anycast (default), unicast, multicast, or directedbroadcast |
||||
|
time_zone: CET; Time Zone Phone is in |
||||
|
dst_offset: 1; Offset from Phone's time when DST is in effect |
||||
|
dst_start_month: April; Month in which DST starts |
||||
|
dst_start_day: ""; Day of month in which DST starts |
||||
|
dst_start_day_of_week: Sun; Day of week in which DST starts |
||||
|
dst_start_week_of_month: 1; Week of month in which DST starts |
||||
|
dst_start_time: 02; Time of day in which DST starts |
||||
|
dst_stop_month: Oct; Month in which DST stops |
||||
|
dst_stop_day: ""; Day of month in which DST stops |
||||
|
dst_stop_day_of_week: Sunday; Day of week in which DST stops |
||||
|
dst_stop_week_of_month: 8; Week of month in which DST stops 8=last week of month |
||||
|
dst_stop_time: 2; Time of day in which DST stops |
||||
|
dst_auto_adjust: 1; Enable(1-Default)/Disable(0) DST automatic adjustment |
||||
|
time_format_24hr: 1; Enable(1 - 24Hr Default)/Disable(0 - 12Hr) |
||||
|
|
||||
|
# Do Not Disturb Control (0-off (default), 1-on, 2-off with no user control, 3-on with no user control) |
||||
|
dnd_control: 2 |
||||
|
|
||||
|
# Caller ID Blocking (0-disabled, 1-enabled, 2-disabled no user control, 3-enabled no user control) |
||||
|
callerid_blocking: 0; (Default is 0 - disabled and sending all calls as anonymous) |
||||
|
|
||||
|
# Anonymous Call Blocking (0-disabled, 1-enabled, 2-disabled no user control, 3-enabled no user control) |
||||
|
anonymous_call_block: 0; (Default is 0 - disabled and blocking of anonymous calls) |
||||
|
|
||||
|
# DTMF AVT Payload (Dynamic payload range for AVT tones - 96-127) |
||||
|
dtmf_avt_payload: 101; Default 101 |
||||
|
|
||||
|
# Sync value of the phone used for remote reset |
||||
|
# Value against which to compare the value in the syncinfo.xml file before a remote reboot is performed |
||||
|
sync: 1; Default 1 |
||||
|
|
||||
|
####### New Parameters added in Release 2.1 ####### |
||||
|
|
||||
|
# Backup Proxy Support |
||||
|
proxy_backup: 0.0.0.0; Dotted IP of Backup Proxy |
||||
|
proxy_backup_port: ""; Backup Proxy port (default is 5060) |
||||
|
|
||||
|
# Emergency Proxy Support |
||||
|
proxy_emergency: 0.0.0.0; Dotted IP of Emergency Proxy |
||||
|
proxy_emergency_port: ""; Emergency Proxy port (default is 5060) |
||||
|
|
||||
|
# Configurable VAD option (voice activation detection) |
||||
|
enable_vad: 0; VAD setting 0-disable (Default), 1-enable |
||||
|
|
||||
|
####### New Parameters added in Release 2.2 ###### |
||||
|
|
||||
|
# NAT/Firewall Traversal |
||||
|
nat_enable: 1; 0-Disabled (default), 1-Enabled |
||||
|
nat_address: ""; WAN IP address of NAT box (dotted IP or DNS A record only) |
||||
|
voip_control_port: 5060; UDP port used for SIP messages (default - 5060) |
||||
|
start_media_port: 16384; Start RTP range for media (default - 16384) |
||||
|
end_media_port: 32766; End RTP range for media (default - 32766) |
||||
|
nat_received_processing: 1; 0-Disabled (default), 1-Enabled |
||||
|
|
||||
|
# Outbound Proxy Support |
||||
|
outbound_proxy: ""; restricted to dotted IP or DNS A record only |
||||
|
outbound_proxy_port: ""; default is 5060 |
||||
|
|
||||
|
####### New Parameter added in Release 3.0 ####### |
||||
|
|
||||
|
# Allow for the bridge on a 3way call to join remaining parties upon hangup |
||||
|
cnf_join_enable: 1; 0-Disabled, 1-Enabled (default) |
||||
|
|
||||
|
####### New Parameters added in Release 3.1 ####### |
||||
|
|
||||
|
# Allow Transfer to be completed while target phone is still ringing |
||||
|
semi_attended_transfer: 1; 0-Disabled, 1-Enabled (default) |
||||
|
|
||||
|
# Telnet Level (enable or disable the ability to Telnet into the phone) |
||||
|
telnet_level: 2; 0-Disabled (default), 1-Enabled, 2-Privileged |
||||
|
|
||||
|
####### New Parameters added in Release 4.0 ####### |
||||
|
|
||||
|
# XML URLs |
||||
|
services_url: ""; URL for external Phone Services |
||||
|
directory_url: ""; URL for external Directory location |
||||
|
logo_url: ""; URL for branding logo to be used on phone display |
||||
|
|
||||
|
# HTTP Proxy Support |
||||
|
http_proxy_addr: ""; Address of HTTP Proxy server |
||||
|
http_proxy_port: ""; Port of HTTP Proxy Server (80-default) |
||||
|
|
||||
|
# Dynamic DNS/TFTP Support |
||||
|
dyn_dns_addr_1: ""; restricted to dotted IP |
||||
|
dyn_dns_addr_2: ""; restricted to dotted IP |
||||
|
dyn_tftp_addr: ""; restricted to dotted IP |
||||
|
|
||||
|
# Remote Party ID |
||||
|
remote_party_id: 0; 0-Disabled (default), 1-Enabled |
||||
|
|
||||
|
####### New Parameters added in Release 4.4 ####### |
||||
|
|
||||
|
# Call Hold Ringback (0-off, 1-on, 2-off with no user control, 3-on with no user control) |
||||
|
call_hold_ringback: 0; Default 0 (Call Hold Ringback feature is off) |
||||
|
|
||||
|
####### New Parameters added in Release 6.0 ####### |
||||
|
|
||||
|
# Dialtone Stutter for MWI |
||||
|
stutter_msg_waiting: 1; 0-Disabled (default), 1-Enabled |
||||
|
|
||||
|
# RTP Call Statistics (SIP BYE/200 OK message exchange) |
||||
|
call_stats: 1; 0-Disabled (default), 1-Enabled |
||||
|
|
||||
|
####### Other parameters ####### |
||||
|
|
||||
|
date_format: D/M/Y; Default is M/D/Y |
||||
|
dscpForAudio: 184; Differentiated Services Code Point (DSCP) specifies the class of service for each audio packet |
||||
|
garp_enable: 0; Gratuitous ARP |
||||
|
language: english; English is the only value that is currently supported |
||||
|
local_cfwd_enable: 1; Whether the phone can do local call forwarding |
||||
|
messages_uri: ""; Configures the voice-mail number that is dialed when the messages button is pressed |
||||
|
network_media_type: Auto; Auto (default), Full100, Half100, Full10, Half10 |
||||
|
network_port2_type: Hub/Switch; Hub/Switch (default), PC (Specifying the PC option and then connecting port 2 to a switch results in spanning-tree loops and network confusion) |
||||
|
rfc_2543_hold: 0; 0 (default) |
||||
|
sip_max_forwards: 70; The phone uses the value specified in this parameter in the Max-Forwards header of the SIP requests that it generates |
||||
|
timer_register_delta: 5; Configures the time interval at which reregistration will occur |
||||
|
|
||||
|
####### Phone specific ###### |
||||
|
|
||||
|
autocomplete: 1; Configures automatic completion of numbers |
||||
|
call_waiting: 1; |
||||
|
phone_label: ""; Text desired to be displayed in upper right corner |
||||
|
#phone_password: cisco; Password to be used for console or telnet login (default: cisco) |
||||
|
phone_prompt: "SIP Phone"; The prompt that will be displayed on console and telnet (default: "SIP Phone") |
||||
|
user_info: none; User classification used when Registering [none (default), phone, ip] |
||||
|
|
||||
|
line1_authname: "" |
||||
|
line2_authname: "" |
||||
|
line3_authname: "" |
||||
|
line4_authname: "" |
||||
|
line5_authname: "" |
||||
|
line6_authname: "" |
||||
|
line1_contact: "" |
||||
|
line2_contact: "" |
||||
|
line3_contact: "" |
||||
|
line4_contact: "" |
||||
|
line5_contact: "" |
||||
|
line6_contact: "" |
||||
|
line1_displayname: "" |
||||
|
line2_displayname: "" |
||||
|
line3_displayname: "" |
||||
|
line4_displayname: "" |
||||
|
line5_displayname: "" |
||||
|
line6_displayname: "" |
||||
|
line1_name: "" |
||||
|
line2_name: "" |
||||
|
line3_name: "" |
||||
|
line4_name: "" |
||||
|
line5_name: "" |
||||
|
line6_name: "" |
||||
|
line1_password: "" |
||||
|
line2_password: "" |
||||
|
line3_password: "" |
||||
|
line4_password: "" |
||||
|
line5_password: "" |
||||
|
line6_password: "" |
||||
|
line1_shortname: "" |
||||
|
line2_shortname: "" |
||||
|
line3_shortname: "" |
||||
|
line4_shortname: "" |
||||
|
line5_shortname: "" |
||||
|
line6_shortname: "" |
||||
|
|
||||
|
call_manager1_addr: "" |
||||
|
call_manager2_addr: "" |
||||
|
call_manager3_addr: "" |
||||
|
call_manager4_addr: "" |
||||
|
call_manager5_addr: "" |
||||
|
call_manager1_sip_port: "" |
||||
|
call_manager2_sip_port: "" |
||||
|
call_manager3_sip_port: "" |
||||
|
call_manager4_sip_port: "" |
||||
|
call_manager5_sip_port: "" |
@ -0,0 +1,3 @@ |
|||||
|
<SYNCINFO> |
||||
|
<IMAGE VERSION="*" SYNC="2"/> |
||||
|
</SYNCINFO> |
@ -0,0 +1,26 @@ |
|||||
|
<Default> |
||||
|
<callManagerGroup> |
||||
|
<members> |
||||
|
<member priority="0"> |
||||
|
<callManager> |
||||
|
<ports> |
||||
|
<ethernetPhonePort>2000</ethernetPhonePort> |
||||
|
<mgcpPorts> |
||||
|
<listen>2427</listen> |
||||
|
<keepAlive>2428</keepAlive> |
||||
|
</mgcpPorts> |
||||
|
</ports> |
||||
|
<processNodeName></processNodeName> |
||||
|
</callManager> |
||||
|
</member> |
||||
|
</members> |
||||
|
</callManagerGroup> |
||||
|
<loadInformation8 model="IP Phone 7940">P0S3-8-12-00</loadInformation8> |
||||
|
<loadInformation7 model="IP Phone 7960">P0S3-8-12-00</loadInformation7> |
||||
|
<authenticationURL></authenticationURL> |
||||
|
<directoryURL></directoryURL> |
||||
|
<idleURL></idleURL> |
||||
|
<informationURL></informationURL> |
||||
|
<messagesURL></messagesURL> |
||||
|
<servicesURL></servicesURL> |
||||
|
</Default> |
@ -0,0 +1,25 @@ |
|||||
|
#!/bin/sh |
||||
|
|
||||
|
cd "$(dirname "$0")" |
||||
|
line="$1" |
||||
|
stamp=/tmp/last_tp |
||||
|
|
||||
|
case "$line" in |
||||
|
32) |
||||
|
snd="tp_prizemi" |
||||
|
;; |
||||
|
44) |
||||
|
snd="tp_prvni" |
||||
|
;; |
||||
|
49) |
||||
|
snd="tp_druhe" |
||||
|
;; |
||||
|
*) |
||||
|
exit |
||||
|
;; |
||||
|
esac |
||||
|
|
||||
|
|
||||
|
if find "$stamp" -mmin -120 | grep -q .; then echo "Too soon"; exit 2; fi |
||||
|
/opt/ksp/ann_play.sh /opt/ksp/sounds/$snd.wav |
||||
|
touch "$stamp" |
@ -0,0 +1,3 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
curl "https://translate.google.com/translate_tts?ie=UTF-8&q="$(perl -MURI::Escape -e 'print uri_escape($ARGV[0])' "$1")"&tl=cs&client=tw-ob" -H 'Referer: http://translate.google.com/' -H 'User-Agent: stagefright/1.2 (Linux;Android 5.0)' |ffmpeg -i - -ar 8000 -ac 1 -y "$2" |
@ -0,0 +1,5 @@ |
|||||
|
#!/bin/bash |
||||
|
|
||||
|
cd "$(dirname "$0")" |
||||
|
|
||||
|
./ann_play_unicast.sh 32 /opt/ksp/sounds/wc_thanks |
@ -0,0 +1,157 @@ |
|||||
|
#!/usr/bin/perl |
||||
|
|
||||
|
use strict; |
||||
|
use warnings; |
||||
|
use utf8; |
||||
|
use feature 'unicode_strings'; |
||||
|
|
||||
|
use Encode; |
||||
|
use Text::Unidecode; |
||||
|
use URI::Escape; |
||||
|
|
||||
|
my %directory; |
||||
|
open my $fh1, '<', '/opt/ksp/www/directory.txt' or die "Cannot open file directory.txt: $!\n"; |
||||
|
open my $fh2, '<', '/opt/ksp/www/directory_external.txt' or die "Cannot open file directory_external.txt: $!\n"; |
||||
|
for my $fh ($fh1, $fh2) { |
||||
|
while (<$fh>) { |
||||
|
chomp; |
||||
|
next if /^#/; |
||||
|
next unless /^\s*(.*?)\s*=\s*([^=]*?)\s*$/; |
||||
|
my ($key, $value) = ($1, $2); |
||||
|
next unless length $key and length $value; |
||||
|
$directory{decode('UTF-8', $key)} = decode('UTF-8', $value); |
||||
|
} |
||||
|
} |
||||
|
close $fh1; |
||||
|
close $fh2; |
||||
|
|
||||
|
sub search { |
||||
|
my ($keyword, $page) = @_; |
||||
|
my @keys = sort keys %directory; |
||||
|
@keys = grep /\Q$keyword\E/i, @keys if length $keyword; |
||||
|
splice @keys, 0, $page * 32; |
||||
|
my $next = splice @keys, 32; |
||||
|
return $next, map { $_ => $directory{$_} } @keys; |
||||
|
} |
||||
|
|
||||
|
sub escape { |
||||
|
my ($text) = @_; |
||||
|
$text =~ s/&/&/g; |
||||
|
$text =~ s/</</g; |
||||
|
$text =~ s/>/>/g; |
||||
|
$text =~ s/\x00//g; |
||||
|
$text =~ s/['"]/_/g; # XML parser does not accept input which contains """ or "'" |
||||
|
$text =~ s/\x86/_/g; # IP Phone firmware crashes when input contains byte 0x86 |
||||
|
return $text; |
||||
|
} |
||||
|
|
||||
|
sub string { |
||||
|
return escape(encode('ISO-8859-1', $_[0], sub { unidecode(chr($_[0])) })); |
||||
|
} |
||||
|
|
||||
|
my $app = sub { |
||||
|
my ($env) = @_; |
||||
|
|
||||
|
return [ '405' ] if $env->{REQUEST_METHOD} !~ /^(?:HEAD|GET)$/; |
||||
|
|
||||
|
my %raw_args = map { (split /=/, $_, 2)[0,1] } split /&/, $env->{QUERY_STRING} // ''; |
||||
|
my %args = map { decode('ISO-8859-1', uri_unescape($_ // '')) } %raw_args; |
||||
|
my $keyword = $args{keyword} // ''; |
||||
|
my $page = $args{page} // ''; |
||||
|
$page = 0 unless $page =~ /^[0-9]+$/; |
||||
|
|
||||
|
my $current_url = $env->{'psgi.url_scheme'} . '://' . $env->{HTTP_HOST} . $env->{PATH_INFO}; |
||||
|
|
||||
|
if (not $args{search}) { |
||||
|
return [ |
||||
|
'200', |
||||
|
[ 'Content-Type' => 'text/xml; charset="ISO-8859-1"' ], |
||||
|
[ <<"EOD" |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneInput> |
||||
|
<Title>Search for an entry</Title> |
||||
|
<Prompt>Enter a search keyword</Prompt> |
||||
|
<URL>$current_url?search=1</URL> |
||||
|
<InputItem> |
||||
|
<DisplayName>Keyword</DisplayName> |
||||
|
<QueryStringParam>keyword</QueryStringParam> |
||||
|
<InputFlags></InputFlags> |
||||
|
<DefaultValue></DefaultValue> |
||||
|
</InputItem> |
||||
|
</CiscoIPPhoneInput> |
||||
|
EOD |
||||
|
], |
||||
|
]; |
||||
|
} |
||||
|
|
||||
|
my $title = length $keyword ? 'Search Result' : 'External Directory'; |
||||
|
|
||||
|
if ($args{end}) { |
||||
|
return [ |
||||
|
'200', |
||||
|
[ 'Content-Type' => 'text/xml; charset="ISO-8859-1"' ], |
||||
|
[ <<"EOD" |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneText> |
||||
|
<Title>$title</Title> |
||||
|
<Text>No more entries</Text> |
||||
|
</CiscoIPPhoneText> |
||||
|
EOD |
||||
|
], |
||||
|
]; |
||||
|
} |
||||
|
|
||||
|
my ($next, %search_result) = search($keyword, $page); |
||||
|
|
||||
|
if (not keys %search_result) { |
||||
|
my $text = length $keyword ? 'No matching entry' : 'Directory is empty'; |
||||
|
return [ |
||||
|
'200', |
||||
|
[ 'Content-Type' => 'text/xml; charset="ISO-8859-1"' ], |
||||
|
[ <<"EOD" |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneText> |
||||
|
<Title>$title</Title> |
||||
|
<Text>$text</Text> |
||||
|
</CiscoIPPhoneText> |
||||
|
EOD |
||||
|
] |
||||
|
]; |
||||
|
} |
||||
|
|
||||
|
my @next_args; |
||||
|
push @next_args, 'search=1'; |
||||
|
push @next_args, "keyword=$raw_args{keyword}" if length $keyword; |
||||
|
push @next_args, 'page=' . ($page+1) if $next; |
||||
|
push @next_args, 'end=1' unless $next; |
||||
|
my $next_url = $current_url . '?' . (join '&', @next_args); |
||||
|
|
||||
|
my $directories = ''; |
||||
|
foreach (sort keys %search_result) { |
||||
|
my $key = $_; |
||||
|
my $name = string($key); |
||||
|
my $telephone = string($search_result{$key}); |
||||
|
$directories .= <<"EOD"; |
||||
|
<DirectoryEntry> |
||||
|
<Name>$name</Name> |
||||
|
<Telephone>$telephone</Telephone> |
||||
|
</DirectoryEntry> |
||||
|
EOD |
||||
|
} |
||||
|
|
||||
|
return [ |
||||
|
'200', |
||||
|
[ |
||||
|
'Content-Type' => 'text/xml; charset="ISO-8859-1"', |
||||
|
'Refresh' => "0; url=$next_url", |
||||
|
], |
||||
|
[ <<"EOD" |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneDirectory> |
||||
|
<Title>$title</Title> |
||||
|
<Prompt>Select an entry</Prompt> |
||||
|
$directories</CiscoIPPhoneDirectory> |
||||
|
EOD |
||||
|
] |
||||
|
]; |
||||
|
}; |
@ -0,0 +1,4 @@ |
|||||
|
[Service] |
||||
|
ExecStart=/usr/bin/uwsgi --ini=/opt/ksp/webapp/directory.uwsgi |
||||
|
[Install] |
||||
|
WantedBy=multi-user.service |
@ -0,0 +1,6 @@ |
|||||
|
[uwsgi] |
||||
|
socket=/tmp/directory.sock |
||||
|
plugin=psgi |
||||
|
psgi=/opt/ksp/webapp/directory.psgi |
||||
|
chmod-socket=666 |
||||
|
|
@ -0,0 +1,33 @@ |
|||||
|
|
||||
|
|
||||
|
my $app = sub { |
||||
|
my ($env) = @_; |
||||
|
my $path = $env->{PATH_INFO}; |
||||
|
my $meth = $env->{REQUEST_METHOD}; |
||||
|
if ($path =~ m|^/hraj/?$| && $meth eq "GET") { |
||||
|
my $r = '<html><body>'; |
||||
|
$r .= qq[<div><form action="/hraj/stop" method="POST"><button style="font-size: 28px;" type="submit">Zastavit vše</button></form></div>]; |
||||
|
opendir my $dir, "/opt/ksp/znelky" or die "Cannot open directory: $!"; |
||||
|
for (readdir $dir) { |
||||
|
next if /^\./; |
||||
|
$r .= qq[<div><form action="/hraj/play/$_" method="POST" onsubmit="return confirm('Přehrát $_?')"><button style="font-size: 28px;" type="submit">$_</button></form></div>]; |
||||
|
} |
||||
|
closedir $dir; |
||||
|
$r .= '</body></html>'; |
||||
|
return [200, ['Content-Type' => 'text/html; charset=UTF-8'], [$r]]; |
||||
|
} elsif ($path =~ m|^/hraj/play/(.*)$| && $meth eq "POST") { |
||||
|
system "/opt/ksp/ann_play.sh", "/opt/ksp/znelky/$1"; |
||||
|
my $r = '<html><body style="font-size: large; ">'; |
||||
|
$r .= qq[Přehrávám $1<br/><a href="/hraj">Zpět</a>]; |
||||
|
$r .= '</body></html>'; |
||||
|
return [200, ['Content-Type' => 'text/html; charset=UTF-8'], [$r]]; |
||||
|
} elsif ($path =~ m|^/hraj/stop$| && $meth eq "POST") { |
||||
|
system "/opt/ksp/ann_stop.sh"; |
||||
|
my $r = '<html><body style="font-size: large; ">'; |
||||
|
$r .= qq[Zastaveno<br/><a href="/hraj">Zpět</a>]; |
||||
|
$r .= '</body></html>'; |
||||
|
return [200, ['Content-Type' => 'text/html; charset=UTF-8'], [$r]]; |
||||
|
} else { |
||||
|
return [404, [], []]; |
||||
|
} |
||||
|
} |
@ -0,0 +1,4 @@ |
|||||
|
[Service] |
||||
|
ExecStart=/usr/bin/uwsgi --ini=/opt/ksp/webapp/hraj.uwsgi |
||||
|
[Install] |
||||
|
WantedBy=multi-user.service |
@ -0,0 +1,7 @@ |
|||||
|
[uwsgi] |
||||
|
|
||||
|
socket=/tmp/hraj.sock |
||||
|
chmod-socket=666 |
||||
|
plugin=psgi |
||||
|
psgi=/opt/ksp/webapp/hraj.pl |
||||
|
|
@ -0,0 +1,676 @@ |
|||||
|
#!/usr/bin/perl |
||||
|
|
||||
|
use strict; |
||||
|
use warnings; |
||||
|
use utf8; |
||||
|
use feature 'unicode_strings'; |
||||
|
|
||||
|
use DBI; |
||||
|
use Encode; |
||||
|
use Net::SIP; |
||||
|
use Net::SIP::Util qw(laddr4dst INETSOCK ip_sockaddr2parts sip_uri2parts); |
||||
|
use Socket; |
||||
|
use Text::Unidecode; |
||||
|
use URI::Escape; |
||||
|
|
||||
|
my $dbfile = '/tmp/messages.db'; # TODO |
||||
|
|
||||
|
my $dbh = DBI->connect("DBI:SQLite:$dbfile", undef, undef, { PrintError => 0, RaiseError => 1, sqlite_unicode => 1 }); |
||||
|
$dbh->do('CREATE TABLE IF NOT EXISTS messages(id INTEGER PRIMARY KEY AUTOINCREMENT, r INT NOT NULL DEFAULT 0, f TEXT NOT NULL, t TEXT NOT NULL, m TEXT NOT NULL)'); |
||||
|
$dbh->do('CREATE INDEX IF NOT EXISTS idx ON messages(r, t)'); |
||||
|
|
||||
|
my $mlsnikfile = '/opt/ksp/mlsnik.db'; |
||||
|
my $mlsnik_dbh = DBI->connect("DBI:SQLite:$mlsnikfile", undef, undef, { PrintError => 0, RaiseError => 1, sqlite_unicode => 1 }); |
||||
|
$mlsnik_dbh->do('CREATE TABLE IF NOT EXISTS nakup(id INTEGER PRIMARY KEY AUTOINCREMENT, meno TEXT NOT NULL, tovar TEXT NOT NULL, cena INT NOT NULL)'); |
||||
|
$mlsnik_dbh->do('CREATE INDEX IF NOT EXISTS idx ON nakup(meno)'); |
||||
|
|
||||
|
sub escape { |
||||
|
my ($text) = @_; |
||||
|
$text =~ s/&/&/g; |
||||
|
$text =~ s/</</g; |
||||
|
$text =~ s/>/>/g; |
||||
|
$text =~ s/\x00//g; |
||||
|
$text =~ s/['"]/_/g; # XML parser does not accept input which contains """ or "'" |
||||
|
$text =~ s/\x86/_/g; # IP Phone firmware crashes when input contains byte 0x86 |
||||
|
return $text; |
||||
|
} |
||||
|
|
||||
|
sub string { |
||||
|
return escape(encode('ISO-8859-1', $_[0], sub { unidecode(chr($_[0])) })); |
||||
|
} |
||||
|
|
||||
|
my @month_names = qw(Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec); |
||||
|
my @day_names = qw(Sun Mon Tue Wed Thu Fri Sat Sun); |
||||
|
sub sip_date { |
||||
|
my @time = gmtime(time()); |
||||
|
return sprintf('%s, %02u %s %04u %02u:%02u:%02u GMT', $day_names[$time[6]], $time[3], $month_names[$time[4]], $time[5] + 1900, $time[2], $time[1], $time[0]); |
||||
|
} |
||||
|
|
||||
|
sub send_sip_message { |
||||
|
my ($from_ip, $to, $message) = @_; |
||||
|
|
||||
|
# HACK: fill sender |
||||
|
$from_ip =~ /\.([0-9]+)$/; |
||||
|
my $user = $1 // 'message'; |
||||
|
my $domain = '172.16.0.1:5062'; |
||||
|
$to .= "\@$domain"; |
||||
|
|
||||
|
my ($host, $recipient) = sip_uri2parts($to); |
||||
|
($host, $recipient) = sip_uri2parts("$to\@$domain") unless defined $host; |
||||
|
return '400 Bad Request' unless defined $host; |
||||
|
|
||||
|
my $port = ($host =~ s/:([0-9]+)$//) ? $1 : undef; |
||||
|
|
||||
|
my $ip = inet_aton($host); |
||||
|
return "478 Unresolvable destination" unless defined $ip; |
||||
|
my $addr = inet_ntoa($ip); |
||||
|
|
||||
|
my $laddr = laddr4dst($addr); |
||||
|
return '478 Unresolvable destination' unless $laddr; |
||||
|
|
||||
|
my $sock = INETSOCK(Proto => 'udp', LocalAddr => $laddr, LocalPort => 0); |
||||
|
return "500 Cannot create socket: $!" unless $sock; |
||||
|
|
||||
|
my $lport = (ip_sockaddr2parts(getsockname($sock)))[1]; |
||||
|
|
||||
|
my $leg = Net::SIP::Leg->new(sock => $sock); |
||||
|
return "500 Cannot create leg: $!" unless $leg; |
||||
|
|
||||
|
my $ua = Net::SIP::Simple->new(from => "<sip:$user\@$domain>", leg => $leg); |
||||
|
return "500 Cannot create SIP user agent: $!" unless $ua; |
||||
|
|
||||
|
my ($stop, $code, $text); |
||||
|
|
||||
|
$ua->{endpoint}->new_request( |
||||
|
'MESSAGE', |
||||
|
{ from => $ua->{from}, to => ('<sip:' . (defined $recipient ? "$recipient\@" : '') . $host . (defined $port ? ":$port" : '') . '>') }, |
||||
|
sub { |
||||
|
(undef, undef, undef, $code, my $packet) = @_; |
||||
|
(undef, $text) = $packet ? $packet->as_parts : (); |
||||
|
$stop = 1; |
||||
|
}, |
||||
|
encode('UTF-8', $message), |
||||
|
uri => ('sip:' . (defined $recipient ? "$recipient\@" : '') . $addr . (defined $port ? ":$port" : '')), |
||||
|
Contact => "<sip:$user\@$laddr:$lport>", |
||||
|
Date => sip_date(), |
||||
|
'Content-Type' => 'text/plain', |
||||
|
'User-Agent' => 'CMXML HTTP Message Sender', |
||||
|
); |
||||
|
|
||||
|
$ua->loop(10, \$stop); |
||||
|
$ua->cleanup(); |
||||
|
|
||||
|
return '408 Request Timeout' unless $stop; |
||||
|
return '400 Bad Request' unless $code and $text; |
||||
|
return "$code $text" unless $code eq '200'; |
||||
|
|
||||
|
return ''; # no error |
||||
|
} |
||||
|
|
||||
|
sub send_message { |
||||
|
my ($env, $service, $args, $current_url, $raw_args) = @_; |
||||
|
|
||||
|
my $recipient = $args->{recipient} // ''; |
||||
|
my $message = $args->{message} // ''; |
||||
|
my $send = $args->{send}; |
||||
|
|
||||
|
if (not $send) { |
||||
|
$recipient = string($recipient); |
||||
|
$message = string($message); |
||||
|
return [ |
||||
|
'200', |
||||
|
[ |
||||
|
'Content-Type' => 'text/xml; charset="ISO-8859-1"', |
||||
|
Expires => '-1', |
||||
|
], |
||||
|
[ <<"EOD" |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneInput> |
||||
|
<Title>Send a new text message</Title> |
||||
|
<Prompt>Send a new text message</Prompt> |
||||
|
<URL>$current_url?service=$service&send=1</URL> |
||||
|
<InputItem> |
||||
|
<DisplayName>Recipient</DisplayName> |
||||
|
<QueryStringParam>recipient</QueryStringParam> |
||||
|
<InputFlags>T</InputFlags> |
||||
|
<DefaultValue>$recipient</DefaultValue> |
||||
|
</InputItem> |
||||
|
<InputItem> |
||||
|
<DisplayName>Message</DisplayName> |
||||
|
<QueryStringParam>message</QueryStringParam> |
||||
|
<InputFlags></InputFlags> |
||||
|
<DefaultValue>$message</DefaultValue> |
||||
|
</InputItem> |
||||
|
</CiscoIPPhoneInput> |
||||
|
EOD |
||||
|
] |
||||
|
]; |
||||
|
} |
||||
|
|
||||
|
my $error = ''; |
||||
|
my $timeout = 0; |
||||
|
|
||||
|
if (not length $recipient) { |
||||
|
$error = "Recipient was not specified"; |
||||
|
$timeout = 3; |
||||
|
} elsif (not length $message) { |
||||
|
$error = "Text of a message was not specified"; |
||||
|
$timeout = 3; |
||||
|
} else { |
||||
|
$error = send_sip_message($env->{REMOTE_ADDR}, $recipient, $message); |
||||
|
} |
||||
|
|
||||
|
my $redirect_url = "$current_url?service=$service"; |
||||
|
|
||||
|
if (length $error) { |
||||
|
$redirect_url .= '&recipient=' . $raw_args->{recipient} if length $recipient; |
||||
|
$redirect_url .= '&message=' . $raw_args->{message} if length $message; |
||||
|
} |
||||
|
|
||||
|
my $text = length $error ? string("ERROR: $error") : 'Message was successfully sent'; |
||||
|
return [ |
||||
|
'200', |
||||
|
[ |
||||
|
'Content-Type' => 'text/xml; charset="ISO-8859-1"', |
||||
|
Expires => '-1', |
||||
|
Refresh => "$timeout; url=$redirect_url", |
||||
|
], |
||||
|
[ <<"EOD" |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneText> |
||||
|
<Title>Send a new text message</Title> |
||||
|
<Text>$text</Text> |
||||
|
</CiscoIPPhoneText> |
||||
|
EOD |
||||
|
] |
||||
|
]; |
||||
|
} |
||||
|
|
||||
|
sub read_message { |
||||
|
my ($env, $service, $args, $current_url) = @_; |
||||
|
|
||||
|
my $next = $args->{next}; |
||||
|
$next = 0 unless $next; |
||||
|
$next = 1 if $next !~ /^[0-9]+$/; |
||||
|
|
||||
|
# HACK: get phone number |
||||
|
my $recipient = $env->{REMOTE_ADDR}; |
||||
|
$recipient =~ s/.*\.//; |
||||
|
|
||||
|
$dbh->do('UPDATE messages SET r=1 WHERE id < ? AND r = 0 AND t = ?', undef, $next, $recipient); |
||||
|
|
||||
|
my ($id, $from, $message) = $dbh->selectrow_array('SELECT id, f, m FROM messages WHERE r = 0 AND t = ? ORDER BY id LIMIT 1', undef, $recipient); |
||||
|
|
||||
|
# HACK: strip SIP domain |
||||
|
(undef, $from) = sip_uri2parts($from); |
||||
|
|
||||
|
$next = $id+1 if defined $id; |
||||
|
|
||||
|
my $timeout = defined $id ? 0 : 10; |
||||
|
my $title = defined $id ? string("From: " . $from) : "Waiting for a message..."; |
||||
|
my $prompt = defined $id ? "Show next message" : "No more unread text messages"; |
||||
|
my $text = defined $id ? string($message) : ''; |
||||
|
|
||||
|
return [ |
||||
|
'200', |
||||
|
[ |
||||
|
'Content-Type' => 'text/xml; charset="ISO-8859-1"', |
||||
|
Expires => '-1', |
||||
|
Refresh => "$timeout; url=$current_url?service=$service&next=$next", |
||||
|
], |
||||
|
[ <<"EOD" |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneText> |
||||
|
<Title>$title</Title> |
||||
|
<Prompt>$prompt</Prompt> |
||||
|
<Text>$text</Text> |
||||
|
</CiscoIPPhoneText> |
||||
|
EOD |
||||
|
] |
||||
|
]; |
||||
|
} |
||||
|
|
||||
|
my %names; |
||||
|
my %orgs; |
||||
|
my %items; |
||||
|
{ |
||||
|
open my $fh, '<:utf8', '/opt/ksp/www/osoby.txt' or die "Cannot open file osoby.txt: $!\n"; |
||||
|
%names = map { chomp($_); my $tmp = unidecode(lc $_); $tmp =~ s/[^a-z0-9]+/_/g; ($tmp => $_) } <$fh>; |
||||
|
close $fh; |
||||
|
} |
||||
|
{ |
||||
|
open my $fh, '<:utf8', '/opt/ksp/www/orgovia.txt' or die "Cannot open file orgovia.txt: $!\n"; |
||||
|
%orgs = map { chomp($_); my $tmp = unidecode(lc $_); $tmp =~ s/[^a-z0-9]+/_/g; ($tmp => $_) } <$fh>; |
||||
|
close $fh; |
||||
|
} |
||||
|
{ |
||||
|
# FORMAT: ascii_query_param TAB Unicode name TAB price Kc TAB available count |
||||
|
open my $fh, '<:utf8', '/opt/ksp/www/tovar.txt' or die "Cannot open file tovar.txt: $!\n"; |
||||
|
%items = map { chomp($_); my ($param, $name, $price, $count) = split /\t+/; ($param => [$name, $price, $count]) } <$fh>; |
||||
|
close $fh; |
||||
|
} |
||||
|
|
||||
|
sub mlsnik { |
||||
|
my ($env, $service, $args, $current_url) = @_; |
||||
|
my $title = string('Mlsník'); |
||||
|
|
||||
|
my $sub = $args->{sub} // ''; |
||||
|
my $name = $args->{name} // ''; |
||||
|
my $item = $args->{item} // ''; |
||||
|
my $confirm = $args->{confirm}; |
||||
|
my $org = $args->{org} // '0'; |
||||
|
|
||||
|
my $string; |
||||
|
my $refresh; |
||||
|
|
||||
|
if ($sub eq 'utrata') { |
||||
|
$title .= string(' - Útrata'); |
||||
|
if (not length $name) { |
||||
|
my $prompt = 'Vyberte osobu'; |
||||
|
$string = <<"EOD"; |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneMenu> |
||||
|
<Title>$title</Title> |
||||
|
<Prompt>$prompt</Prompt> |
||||
|
EOD |
||||
|
if (not $org) { |
||||
|
for my $name (sort { $names{$a} cmp $names{$b} } keys %names) { |
||||
|
my $info = string($names{$name}); |
||||
|
$string .= <<"EOD"; |
||||
|
<MenuItem> |
||||
|
<Name>$info</Name> |
||||
|
<URL>$current_url?service=$service&sub=utrata&org=0&name=$name</URL> |
||||
|
</MenuItem> |
||||
|
EOD |
||||
|
} |
||||
|
$string .= <<"EOD"; |
||||
|
<MenuItem> |
||||
|
<Name>Orgovia</Name> |
||||
|
<URL>$current_url?service=$service&sub=utrata&org=1</URL> |
||||
|
</MenuItem> |
||||
|
EOD |
||||
|
$string .= '</CiscoIPPhoneMenu>'; |
||||
|
} else { |
||||
|
for my $name (sort { $orgs{$a} cmp $orgs{$b} } keys %orgs) { |
||||
|
my $info = string($orgs{$name}); |
||||
|
$string .= <<"EOD"; |
||||
|
<MenuItem> |
||||
|
<Name>$info</Name> |
||||
|
<URL>$current_url?service=$service&sub=utrata&org=1&name=$name</URL> |
||||
|
</MenuItem> |
||||
|
EOD |
||||
|
} |
||||
|
} |
||||
|
$string .= '</CiscoIPPhoneMenu>'; |
||||
|
} else { |
||||
|
$title = string('Útrata pre ' . ($org ? $orgs{$name} : $names{$name})); |
||||
|
$string = <<"EOD"; |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneMenu> |
||||
|
<Title>$title</Title> |
||||
|
EOD |
||||
|
my @items = $mlsnik_dbh->selectall_array('SELECT tovar,COUNT(tovar),SUM(cena) FROM nakup WHERE meno = ? GROUP BY tovar', undef, $name); |
||||
|
foreach (@items) { |
||||
|
my ($tovar, $count, $cena) = @{$_}; |
||||
|
my $item = $items{$tovar}->[0]; |
||||
|
my $info = string("${count}x $item ... $cena Kč"); |
||||
|
$string .= <<"EOD"; |
||||
|
<MenuItem> |
||||
|
<Name>$info</Name> |
||||
|
<URL>$current_url?service=$service&sub=utrata&org=$org&name=$name</URL> |
||||
|
</MenuItem> |
||||
|
EOD |
||||
|
} |
||||
|
my $cena = $mlsnik_dbh->selectrow_array('SELECT SUM(cena) FROM nakup WHERE meno = ?', undef, $name); |
||||
|
$cena ||= 0; |
||||
|
my $info = string("Celkom ... $cena Kč"); |
||||
|
$string .= <<"EOD"; |
||||
|
<MenuItem> |
||||
|
<Name>$info</Name> |
||||
|
<URL>$current_url?service=$service&sub=utrata&org=$org&name=$name</URL> |
||||
|
</MenuItem> |
||||
|
EOD |
||||
|
$string .= '</CiscoIPPhoneMenu>'; |
||||
|
} |
||||
|
} elsif ($sub eq 'kupa') { |
||||
|
$title .= string(' - Kúpa'); |
||||
|
my $prompt = 'Vyberte osobu'; |
||||
|
$string = <<"EOD"; |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneMenu> |
||||
|
<Title>$title</Title> |
||||
|
<Prompt>$prompt</Prompt> |
||||
|
EOD |
||||
|
if (not length $name) { |
||||
|
if (not $org) { |
||||
|
for my $name (sort { $names{$a} cmp $names{$b} } keys %names) { |
||||
|
my $info = string($names{$name}); |
||||
|
$string .= <<"EOD"; |
||||
|
<MenuItem> |
||||
|
<Name>$info</Name> |
||||
|
<URL>$current_url?service=$service&sub=kupa&org=0&name=$name</URL> |
||||
|
</MenuItem> |
||||
|
EOD |
||||
|
} |
||||
|
$string .= <<"EOD"; |
||||
|
<MenuItem> |
||||
|
<Name>Orgovia</Name> |
||||
|
<URL>$current_url?service=$service&sub=kupa&org=1</URL> |
||||
|
</MenuItem> |
||||
|
EOD |
||||
|
} else { |
||||
|
for my $name (sort { $orgs{$a} cmp $orgs{$b} } keys %orgs) { |
||||
|
my $info = string($orgs{$name}); |
||||
|
$string .= <<"EOD"; |
||||
|
<MenuItem> |
||||
|
<Name>$info</Name> |
||||
|
<URL>$current_url?service=$service&sub=kupa&org=1&name=$name</URL> |
||||
|
</MenuItem> |
||||
|
EOD |
||||
|
} |
||||
|
} |
||||
|
$string .= '</CiscoIPPhoneMenu>'; |
||||
|
} elsif (not length $item) { |
||||
|
$title = string("Kúpiť pre " . ($org ? $orgs{$name} : $names{$name})); |
||||
|
$string = <<"EOD"; |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneMenu> |
||||
|
<Title>$title</Title> |
||||
|
<Prompt>Vyberte tovar</Prompt> |
||||
|
EOD |
||||
|
for my $item (sort { $items{$a}->[0] cmp $items{$b}->[0] } keys %items) { |
||||
|
next unless $items{$item}->[2]; |
||||
|
my $info = string($items{$item}->[0] . " - " . $items{$item}->[1] . " Kč"); |
||||
|
$string .= <<"EOD"; |
||||
|
<MenuItem> |
||||
|
<Name>$info</Name> |
||||
|
<URL>$current_url?service=$service&sub=kupa&org=$org&name=$name&item=$item</URL> |
||||
|
</MenuItem> |
||||
|
EOD |
||||
|
} |
||||
|
$string .= '</CiscoIPPhoneMenu>'; |
||||
|
} elsif (not $confirm) { |
||||
|
my $prompt = string("Potvrdiť"); |
||||
|
my $info = string(($org ? $orgs{$name} : $names{$name}) . " si zakupuje tovar " . $items{$item}->[0] . " za " . $items{$item}->[1] . " Kč"); |
||||
|
$string = <<"EOD"; |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneMenu> |
||||
|
<Title>$title</Title> |
||||
|
<Prompt>$prompt</Prompt> |
||||
|
<MenuItem> |
||||
|
<Name>$info</Name> |
||||
|
<URL>$current_url?service=$service&sub=kupa&org=$org&name=$name&item=$item&confirm=1</URL> |
||||
|
</MenuItem> |
||||
|
</CiscoIPPhoneMenu> |
||||
|
EOD |
||||
|
} else { |
||||
|
$mlsnik_dbh->do('INSERT INTO nakup(meno, tovar, cena) VALUES(?, ?, ?)', undef, $name, $item, $items{$item}->[1]); |
||||
|
|
||||
|
$refresh = "2; url=$current_url"; |
||||
|
my $info = string("Potvrdené"); |
||||
|
$string = <<"EOD"; |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneText> |
||||
|
<Title>$title</Title> |
||||
|
<Text>$info</Text> |
||||
|
</CiscoIPPhoneText> |
||||
|
EOD |
||||
|
} |
||||
|
} else { |
||||
|
my $prompt = string('Vyberte možnosť'); |
||||
|
my $item1 = string('Kúpiť tovar'); |
||||
|
my $item2 = string('Zobraziť útratu'); |
||||
|
$string = <<"EOD"; |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneMenu> |
||||
|
<Title>$title</Title> |
||||
|
<Prompt>$prompt</Prompt> |
||||
|
<MenuItem> |
||||
|
<Name>$item1</Name> |
||||
|
<URL>$current_url?service=$service&sub=kupa</URL> |
||||
|
</MenuItem> |
||||
|
<MenuItem> |
||||
|
<Name>$item2</Name> |
||||
|
<URL>$current_url?service=$service&sub=utrata</URL> |
||||
|
</MenuItem> |
||||
|
</CiscoIPPhoneMenu> |
||||
|
EOD |
||||
|
} |
||||
|
|
||||
|
utf8::downgrade($string); # Workaround bug in PSGI |
||||
|
|
||||
|
return [ |
||||
|
'200', |
||||
|
[ |
||||
|
'Content-Type' => 'text/xml; charset="ISO-8859-1"', |
||||
|
Expires => '-1', |
||||
|
($refresh ? (Refresh => $refresh) : ()), |
||||
|
], |
||||
|
[ |
||||
|
$string |
||||
|
] |
||||
|
]; |
||||
|
} |
||||
|
|
||||
|
sub weather { |
||||
|
my ($env, $service, $args, $current_url) = @_; |
||||
|
my $title = string('Weather Forecast'); |
||||
|
my @items; |
||||
|
if (open my $fh, '<:utf8', '/tmp/weather.txt') { |
||||
|
chomp(@items = <$fh>); |
||||
|
close $fh; |
||||
|
} else { |
||||
|
push @items, 'ERROR: Cannot open /tmp/weather.txt'; |
||||
|
} |
||||
|
push @items, 'ERROR: /tmp/weather.txt is empty' unless @items; |
||||
|
my $items; |
||||
|
foreach (@items) { |
||||
|
my $text = string($_); |
||||
|
$items .= <<"EOD"; |
||||
|
<MenuItem> |
||||
|
<Name>$text</Name> |
||||
|
<URL>$current_url?service=$service</URL> |
||||
|
</MenuItem> |
||||
|
EOD |
||||
|
} |
||||
|
|
||||
|
my $string = <<"EOD"; |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneMenu> |
||||
|
<Title>$title</Title> |
||||
|
<Prompt>Update</Prompt> |
||||
|
$items</CiscoIPPhoneMenu> |
||||
|
EOD |
||||
|
utf8::downgrade($string); # Workaround bug in PSGI |
||||
|
|
||||
|
return [ |
||||
|
'200', |
||||
|
[ |
||||
|
'Content-Type' => 'text/xml; charset="ISO-8859-1"', |
||||
|
Expires => '-1', |
||||
|
Refresh => "30; url=$current_url?service=$service", |
||||
|
], |
||||
|
[ |
||||
|
$string |
||||
|
], |
||||
|
]; |
||||
|
} |
||||
|
|
||||
|
sub status { |
||||
|
my ($env, $service, $args, $current_url) = @_; |
||||
|
my $title = string('Error status log'); |
||||
|
my @items; |
||||
|
if (open my $fh, '<:utf8', '/tmp/error.log') { |
||||
|
chomp(@items = <$fh>); |
||||
|
close $fh; |
||||
|
} else { |
||||
|
push @items, 'ERROR: Cannot open error log'; |
||||
|
} |
||||
|
push @items, 'No errors' unless @items; |
||||
|
my $items; |
||||
|
foreach (@items) { |
||||
|
my $text = string($_); |
||||
|
$items .= <<"EOD"; |
||||
|
<MenuItem> |
||||
|
<Name>$text</Name> |
||||
|
<URL>$current_url?service=$service</URL> |
||||
|
</MenuItem> |
||||
|
EOD |
||||
|
} |
||||
|
|
||||
|
my $string = <<"EOD"; |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneMenu> |
||||
|
<Title>$title</Title> |
||||
|
<Prompt>Update</Prompt> |
||||
|
$items</CiscoIPPhoneMenu> |
||||
|
EOD |
||||
|
utf8::downgrade($string); # Workaround bug in PSGI |
||||
|
|
||||
|
return [ |
||||
|
'200', |
||||
|
[ |
||||
|
'Content-Type' => 'text/xml; charset="ISO-8859-1"', |
||||
|
Expires => '-1', |
||||
|
Refresh => "30; url=$current_url?service=$service", |
||||
|
], |
||||
|
[ |
||||
|
$string |
||||
|
], |
||||
|
]; |
||||
|
} |
||||
|
|
||||
|
my %services = ( |
||||
|
send_message => [ 'Send a new text message' => \&send_message, 1 ], |
||||
|
read_message => [ 'Show unread text messages' => \&read_message, 2 ], |
||||
|
mlsnik => [ 'Mlsnik' => \&mlsnik, 3 ], |
||||
|
weather => [ 'Weather Forecast - yr.no' => \&weather, 4 ], |
||||
|
status => [ 'Error status log' => \&status, 5 ], |
||||
|
); |
||||
|
|
||||
|
sub wc_paper { |
||||
|
my ($env, $service, $args, $current_url, $raw_args, $line) = @_; |
||||
|
my ($sec, $min, $hour) = localtime(); |
||||
|
if ($hour >= 23 || $hour < 7) { # Night time |
||||
|
return [ |
||||
|
'200', |
||||
|
[ |
||||
|
'Content-Type' => 'text/xml; charset="ISO-8859-1"', |
||||
|
Expires => '-1', |
||||
|
], |
||||
|
[ |
||||
|
<<"EOD" |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneText> |
||||
|
<Title>WC: I need a toilet paper</Title> |
||||
|
<Text>This feature is disabled during night time.</Text> |
||||
|
</CiscoIPPhoneText> |
||||
|
EOD |
||||
|
], |
||||
|
]; |
||||
|
} |
||||
|
if ($args->{confirm}) { |
||||
|
say STDERR "running: '/opt/ksp/toilet_paper.sh $line &'"; |
||||
|
system("sh", "-c", "/opt/ksp/toilet_paper.sh $line &"); |
||||
|
} |
||||
|
return [ |
||||
|
'200', |
||||
|
[ |
||||
|
'Content-Type' => 'text/xml; charset="ISO-8859-1"', |
||||
|
Expires => '-1', |
||||
|
], |
||||
|
[ |
||||
|
$args->{confirm} ? <<"EOD" |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneText> |
||||
|
<Title>WC: I need a toilet paper</Title> |
||||
|
<Text>Request for a new toilet paper was sent.</Text> |
||||
|
</CiscoIPPhoneText> |
||||
|
EOD |
||||
|
: <<"EOD" |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneMenu> |
||||
|
<Title>WC: I need a toilet paper</Title> |
||||
|
<Prompt>Confirm</Prompt> |
||||
|
<MenuItem> |
||||
|
<Name>Is a toilet paper really missing? Requeust for a new one.</Name> |
||||
|
<URL>$current_url?service=$service&confirm=1</URL> |
||||
|
</MenuItem> |
||||
|
</CiscoIPPhoneMenu> |
||||
|
EOD |
||||
|
], |
||||
|
]; |
||||
|
} |
||||
|
|
||||
|
sub wc_call_help { |
||||
|
my ($env) = @_; |
||||
|
return [ |
||||
|
'200', |
||||
|
[ 'Content-Type' => 'text/xml; charset="ISO-8859-1"' ], |
||||
|
[ <<"EOD" |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneDirectory> |
||||
|
<Title>WC: Call for HELP</Title> |
||||
|
<DirectoryEntry> |
||||
|
<Name>Call for HELP</Name> |
||||
|
<Telephone>130</Telephone> |
||||
|
</DirectoryEntry> |
||||
|
</CiscoIPPhoneDirectory> |
||||
|
EOD |
||||
|
] |
||||
|
]; |
||||
|
} |
||||
|
|
||||
|
my %wc_services = ( |
||||
|
wc_paper => [ 'WC: I need a toilet paper' => \&wc_paper ], |
||||
|
wc_call_help => [ 'WC: Call for HELP' => \&wc_call_help ], |
||||
|
); |
||||
|
|
||||
|
my $app = sub { |
||||
|
my ($env) = @_; |
||||
|
|
||||
|
return [ '405' ] if $env->{REQUEST_METHOD} !~ /^(?:HEAD|GET)$/; |
||||
|
|
||||
|
my %raw_args = map { (split /=/, $_, 2)[0,1] } split /&/, $env->{QUERY_STRING} // ''; |
||||
|
my %args = map { decode('ISO-8859-1', uri_unescape($_ // '')) } %raw_args; |
||||
|
my $service = $args{service} // ''; |
||||
|
|
||||
|
my $current_url = $env->{'psgi.url_scheme'} . '://' . $env->{HTTP_HOST} . $env->{PATH_INFO}; |
||||
|
|
||||
|
# HACK: get line |
||||
|
my $line = $env->{REMOTE_ADDR}; |
||||
|
$line =~ s/.*\.//; |
||||
|
|
||||
|
return $wc_services{$service}->[1]->($env, $service, \%args, $current_url, \%raw_args, $line) if exists $wc_services{$service}; |
||||
|
return $services{$service}->[1]->($env, $service, \%args, $current_url, \%raw_args, $line) if exists $services{$service}; |
||||
|
|
||||
|
return [ '404' ] if length $service; |
||||
|
|
||||
|
my $services = ''; |
||||
|
my @services_keys = sort { $services{$a}->[2] cmp $services{$b}->[2] } keys %services; |
||||
|
@services_keys = grep !/mlsnik/, @services_keys unless $line =~ /^(?:36|37|2.|33)$/; |
||||
|
unshift @services_keys, sort { $wc_services{$a}->[0] cmp $wc_services{$b}->[0] } keys %wc_services if $line =~ /^(?:32|44|49)$/; |
||||
|
foreach (@services_keys) { |
||||
|
my $name = string(exists $services{$_} ? $services{$_}->[0] : $wc_services{$_}->[0]); |
||||
|
my $url = "$current_url?service=$_"; |
||||
|
$services .= <<"EOD"; |
||||
|
<MenuItem> |
||||
|
<Name>$name</Name> |
||||
|
<URL>$url</URL> |
||||
|
</MenuItem> |
||||
|
EOD |
||||
|
} |
||||
|
|
||||
|
return [ |
||||
|
'200', |
||||
|
[ 'Content-Type' => 'text/xml; charset="ISO-8859-1"' ], |
||||
|
[ <<"EOD" |
||||
|
<?xml version="1.0" encoding="ISO-8859-1"?> |
||||
|
<CiscoIPPhoneMenu> |
||||
|
<Title>Services for line $line</Title> |
||||
|
<Prompt>Select option</Prompt> |
||||
|
$services</CiscoIPPhoneMenu> |
||||
|
EOD |
||||
|
] |
||||
|
]; |
||||
|
}; |
@ -0,0 +1,4 @@ |
|||||
|
[Service] |
||||
|
ExecStart=/usr/bin/uwsgi --ini=/opt/ksp/webapp/services.uwsgi |
||||
|
[Install] |
||||
|
WantedBy=multi-user.service |
@ -0,0 +1,6 @@ |
|||||
|
[uwsgi] |
||||
|
socket=/tmp/services.sock |
||||
|
plugin=psgi |
||||
|
psgi=/opt/ksp/webapp/services.psgi |
||||
|
chmod-socket=666 |
||||
|
|
@ -0,0 +1,13 @@ |
|||||
|
Technická podpora FBI = 910119352 |
||||
|
HR linka = 4445 |
||||
|
Hlasová schránka = 131 |
||||
|
Konference 0 = 110 |
||||
|
Konference 1 = 111 |
||||
|
Konference 2 = 112 |
||||
|
Konference 3 = 113 |
||||
|
Konference 4 = 114 |
||||
|
Konference 5 = 115 |
||||
|
Konference 6 = 116 |
||||
|
Konference 7 = 117 |
||||
|
Konference 8 = 118 |
||||
|
Konference 9 = 119 |
After Width: | Height: | Size: 6.1 KiB |
@ -0,0 +1,2 @@ |
|||||
|
Org 1 |
||||
|
Org 2 |
@ -0,0 +1,2 @@ |
|||||
|
Meno 1 |
||||
|
Meno 2 |
@ -0,0 +1,34 @@ |
|||||
|
coca_cola Coca Cola 1.75 22 0 |
||||
|
pepsi_cola Pepsi Cola 2.5 20 0 |
||||
|
minonky Miňonky 10 1 |
||||
|
kastany Kaštany 11 0 |
||||
|
tofik Tofík 5 0 |
||||
|
musli Müsli tyčinka 5 1 |
||||
|
fin_carre_200 Fin Carré 200g (velk) 33 0 |
||||
|
fin_carre_100 Fin Carré 100g (malá) 16 1 |
||||
|
fin_carre_nois Fin Carré Noisette 20 1 |
||||
|
fin_carre_74 Fin Carré 74% 20 0 |
||||
|
piskoy_coko Piškoty v čokoládě 13 0 |
||||
|
zele_jelly Želé Rainbow Jelly 10 0 |
||||
|
syrove_tycinky Sýrové tyčinky 15 1 |
||||
|
arasidy_pikan Arašídy pikantní 17 0 |
||||
|
chipsy_snack Chipsy Snack 150g 16 0 |
||||
|
syrove_koule Sýrové koule / Snack 8 0 |
||||
|
mrkev Mrkev 1 0 |
||||
|
chipsy_bohemia Chipsy Bohemia 130g 30 0 |
||||
|
kofola_15 Kofola 1.5 26 0 |
||||
|
oreo Oreo 44g 11 0 |
||||
|
pepsi_cola15 Pepsi Cola 1.5 18 0 |
||||
|
import_paper Historické nákupy 0 0 |
||||
|
kofola_2 Kofola 2l 15 1 |
||||
|
bramb_tycinky Bramborové tyčinky 15 1 |
||||
|
chipsy_ahb Chipsy 22 1 |
||||
|
arasidy_sl_kar Arašídy slaný karam. 30 1 |
||||
|
arasidy_sol Arašídy solené 11 1 |
||||
|
arasid_krup Arašídové křupky 9 1 |
||||
|
banán Banán 3 1 |
||||
|
zlate_polom Zlaté polomáčané 17 1 |
||||
|
napoli_or Manner snack 4 1 |
||||
|
happy_day Happy day džus 30 1 |
||||
|
stud_pecet Studenská pečeť 30 1 |
||||
|
mrkev_2 Mrkev 2 1 |