PERL-EMAIL-AGI

  1. !/usr/bin/perl

  1. Added by Suretec Systems Ltd. - http://www.suretecsystems.com - 28/04/2006
use warnings;
use strict;



 use Asterisk::AGI;
 use File::Basename;
 use Mail::IMAPClient;
 use MIME::Parser;
 use Digest::MD5 qw(md5_hex);
 use POSIX;

 my $DEBUG    = 1;
 my $T2WP     = "/usr/bin/";            # path to text2wave(1) binary
 my $SOUNDDIR = '/var/lib/asterisk/sounds';
 my $SOUNDTMP = $SOUNDDIR . '/tts';

 my $ZERO =   ord('0');                 # ASCII codes?
 my $ONE =    ord('1');                 # Give me a break!
 my $TWO =    ord('2');
 my $THREE =  ord('3');
 my $FOUR =   ord('4');
 my $FIVE =   ord('5');
 my $SIX =    ord('6');
 my $SEVEN =  ord('7');
 my $EIGHT =  ord('8');
 my $NINE =   ord('9');
 my $STAR =   ord('*');
 my $POUND =  ord('#');

 my $MAINKEYS = '123#';                 # keys recognized by main menu
 my $LISTKEYS = '34567*#';              # keys recognized by list menu
 my $BODYKEYS = '345679*#';             # .. by play msg body
 my $AMSGKEYS = '3579*#';               # .. when playing a selected msg

 my %MONTHV = ( Jan => 0, Feb => 1,  'Mar' => 2,
                Apr => 3, May => 4,  'Jun' => 5,
               Jul => 6, Aug => 7,  'Sep' => 8,
               Oct => 9, Nov => 10, 'Dec' => 11  );

 my @MONTHN = ( 'January', 'February', 'March', 'April', 'May', 'June',
                'July', 'August', 'September', 'October', 'November', 'December');

 my @DAYN   = ( 'Sunday', 'Monday', 'Tuesday',
                'Wednesday', 'Thursday', 'Friday', 'Saturday');

 my $ONEDAY = (60 * 60) * 24;

 #-----------------------------------------------------------------------------
 # Notes:  must call with username, password, imap server                    #
 #-----------------------------------------------------------------------------

 die "Usage: $0 user&pass&server" if ($#ARGV != 0);

 my @auth = split('&', $ARGV[0]);
 die "Usage: $0 user&pass&server" if ($#auth != 2);

 my $AGI  = new Asterisk::AGI;
 my %input = $AGI->ReadParse();

 $AGI->setcallback(\&myExit);           # Hangup/Error detection

 my $IMAP = Mail::IMAPClient->new(
            User    => $auth[0],
            Password => $auth[1],
            Server  => $auth[2]);

 if (! $IMAP->login)
   {
   $AGI->verbose("Unable to login ($auth[0])") if ($DEBUG);
   #$AGI->stream_file('?????', '""');
   play_text("Sorry, I could not login to the IMAP server!");
   myExit("Unable to login ($auth[0])");
   }

 if ( ! $IMAP->select("INBOX"))
   {
   $AGI->verbose("Unable to select INBOX", 1) if ($DEBUG);
   #$AGI->stream_file('?????', '""');
   play_text("Sorry, I could not find your inbox!");
   myExit("Unable to select Inbox");
   }

 $IMAP->Peek(1) if ($DEBUG);

 my %newMSGs;

 my $newmsgcnt = 0;
 my @seen   = $IMAP->seen;
 my @all    = $IMAP->messages;
 my $msgcnt = $#all;

 %hseen = ();
 foreach $_ (@seen)
   {
   $hseen{$_} = 1;
   }

 foreach $msg (@all)
   {
   if ( ! exists($hseen{$msg}))
     {
     $newMSGs{$msg} = 1;
     $newmsgcnt++;
     }
   }

 my $key = $AGI->stream_file('vm-youhave', $MAINKEYS);

 if ($newmsgcnt == 0)
   {
   $key = $AGI->stream_file('no', $MAINKEYS) if ($key == 0);
   }
 else
   {
   $key = $AGI->say_number($newmsgcnt, $MAINKEYS) if ($key == 0);
   }

 $key = $AGI->stream_file('new', $MAINKEYS) if ($key == 0);
 $key = $AGI->stream_file((($newmsgcnt == 1) ? 'vm-message' : 'vm-messages'), $MAINKEYS) if ($key == 0);

 sleep(1) if ($key == 0);

 main_menu($key);  # Never returns..
 myExit("Mission Improbable!");

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub find_a_msg
 #                                                                          #
 # User wants to read a single message by #; find out what number!          #
 #                                                                          #
 {
 my $number ="";

 #my $key = $AGI->stream_file('?????', "0123456789#*") if ($key == 0);
 my $key = play_text("Enter the message number, followed by the pound sign", "0123456789#*");

 while ($key != $POUND)
   {
   return(0) if ($key == $STAR);
   last      if ($key == $POUND);

   $number .= $key if ($key != 0);
   $AGI->wait_for_digit(7);

   if (($number eq "") && ($key == 0))
     {
     #$key = $AGI->stream_file('?????', "0123456789#*") if ($key == 0);
     $key = play_text("Enter the message number, followed by the pound sign", "0123456789#*");
     }
   else
     {
     #$key = $AGI->stream_file('?????', "0123456789#*") if ($key == 0);
     $key = play_text("You must end with the pound sign.  Push the star key to abort.");
     }
   }

 if ( ! $IMAP->get_header($number, 'Date'))
   {
   #$key = $AGI->stream_file('?????', '""');
   play_text("Sorry, message number " . $number . " could not be located.");
   sleep(1);
   return(0);
   }

 $key = play_number_header($number, 0, $AMSGKEYS);
 $key = play_number_body2($number, $key);
 return(0);
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub hangup
 #                                                                           #
 # User hit '#', end the session.                                            #
 #                                                                           #
 {
 $AGI->stream_file('goodbye', '""');
 $AGI->hangup();
 myExit();
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub list_messages
 #                                                                          #
 # Sequentially play each new message (newest first)                        #
 #                                                                          #
 {
 my ($new) = @_;                                # are we considering only 'unseen'?
 my $key = 0;

 if (($new) && ($newmsgcnt < 1))
   {
   $key = $AGI->stream_file('vm-youhave', $MAINKEYS);
   $key = $AGI->stream_file('no', $MAINKEYS) if ($key == 0);
   $key = $AGI->stream_file('new', $MAINKEYS) if ($key == 0);
   $key = $AGI->stream_file('vm-messages', $MAINKEYS) if ($key == 0);
   return($key);
   }

 for ($i=$msgcnt; $i >=0; $i--)
   {
   $msg = $all[$i];

   next if (($new) && (! defined $newMSGs{$msg}));

   # Note that "$key < 0" below does NOT imply 'hungup or error'.
   # Rather, it's part of a kludge to pass keys through from the submenu

   $key = play_msg_header($msg, $new, $LISTKEYS) unless ($key < 0);

   $key = 0 - $key if ($key < 0) ;
   $key = 0 if ($key == $EIGHT);                # kludge to skip hdr on return from body

   while ($key == 0)
     {
     $key = play_list_menu();
     $key = $AGI->wait_for_digit(10) if ($key == 0);
     }

   if ($key != 0)
     {
     if ($key == $THREE)                        # Repeat current hdr
       {
       $i++; next;                      # (Loop offsets increment)
       }
     elsif ($key == $FOUR)              # Play prev (newer) message
       {
       my $newmsg = -1;
                                        # this is fairly ugly...
       if ($i < $msgcnt)
         {
         if ($new)                      # (find prev 'new' message)
           {
          for $j ($i+1 .. $msgcnt)
            {
            if (defined $newMSGs{$all[$j]})
              {
              $newmsg = $j;
              last;
              }
            }
          }
         else                           # (or select prev 'any' message)
           {
          $newmsg = $i + 1;
           }
        }

       if ($newmsg < 0)
         {
        $key = $AGI->stream_file('vm-nomore', $LISTKEYS);
        }
       else
         {
        $i = $newmsg + 1;               # (account for loop decrement)
        next;
        }
       }
     elsif ($key == $FIVE)              # Play message body for this message
       {
       $key = play_msg_body($msg);

       if ($key != $THREE)              # (key passthrough kludge)
          {
          $key = ($key > 0) ? (0 - $key) : (0 - $EIGHT);
         }
       next;
       }
     elsif ($key == $SIX)               # Play next (older) message
       {
       my $newmsg = -1;

       if ($i > 0)
         {
         if ($new)                      # (find next 'new' message)
           {
           for ($j = $i-1; $j >= 0; $j--)
            {
            if (defined $newMSGs{$all[$j]})
              {
              $newmsg = $j;
              last;
              }
            }
          }
        else
           {
           $newmsg = $i - 1;
          }
        }

       if ($newmsg < 0)
         {
        $key = $AGI->stream_file('vm-nomore', $LISTKEYS);
        }
       else
         {
        $i = $newmsg + 1;               # (account for loop decrement)
        next;
        }
       }
     elsif ($key == $SEVEN)             # Delete message
       {
       my @m = ($msg);
       my $c = $IMAP->delete_message(@m);
       if (($DEBUG) && ($c != 1))
         {
        $AGI->verbose("delete_messge returned: " . $c, 1) if ($DEBUG);
        }
       $IMAP->stream_file('vm-deleted', '""');
       }
     elsif ($key == $STAR) { return(0); }
     elsif ($key == $POUND) { hangup(); }
     else
       {
       $AGI->verbose('PANIC [#1] - ' . $key . '!!!',  1) if ($DEBUG);
       $key = 0;
       }
     }
   }

 return(0);             # non-executable?
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub main_menu
 #                                                                          #
 # Play and interpret the main menu                                         #
 #                                                                          #
 {
 my ($key) = @_;

 while (1)
   {
   while ($key == 0)
     {
     $key = play_main_menu();
     $key = $AGI->wait_for_digit(10) if ($key == 0);
     }

   if ($key == $ONE)      { $key = list_messages(1); }
   elsif ($key == $TWO)   { $key = list_messages(0); }
   elsif ($key == $THREE) { $key = find_a_msg(); }
   elsif ($key == $POUND)
     {
     hangup();
     }
   else
    {
    $AGI->verbose('PANIC [#0] - ' . $key . '!!!',  1) if ($DEBUG);
    $key = 0;
    }
   # Note: INVALID keys are not passed through from stream_file()
   }

 # Only exits via hangup() option
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub myExit
 #                                                                          #
 # Terminate w/ cleanup                                                     #
 #                                                                          #
 {
 ($msg) = @_;

 $IMAP->close;

 if ($msg != '')
   {
   $AGI->verbose("Exited: " . $msg) if ($DEBUG);
   die $msg;
   }
 exit;
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub parse_message_text
 #                                                                          #
 # Find something in the message we can 'read' to the user                  #
 #                                                                          #
 {
 my ($msgtxt) = @_;

 my $newtxt = '';
 my $parser =  new MIME::Parser;

 $parser->output_under('/tmp');
 $parser->decode_headers(1);
 $parser->extract_nested_messages(0);
 $parser->ignore_errors(1);

 my $entity = $parser->parse_data($msgtxt);

 if ($entity->bodyhandle)
   {
   $newtxt = $entity->bodyhandle->as_string;
   }
 elsif ($entity->parts > -1)
   {
   $newtxt = $entity->parts(0);
   }
 else
   {
   $newtxt = "Unable to parse message text!";
   }

 return($newtxt);
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_list_menu
 #                                                                          #
 # Play the 'listing messages' menu                                         #
 #                                                                          #
 {
 my $key = $AGI->stream_file('vm-press', $LISTKEYS);
 $key = $AGI->stream_file('digits/3', $LISTKEYS) if ($key == 0);
 $key = $AGI->stream_file('to-hear-msg-envelope', $LISTKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-prev', $LISTKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-press', $LISTKEYS) if ($key == 0);
 $key = $AGI->stream_file('digits/5', $LISTKEYS) if ($key == 0);
 $key = $AGI->stream_file('to-listen-to-it', $LISTKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-next', $LISTKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-starmain', $LISTKEYS) if ($key == 0);

 $key = $AGI->stream_file('to-hang-up', $LISTKEYS) if ($key == 0);
 $key = $AGI->stream_file('vm-press', $LISTKEYS) if ($key == 0);
 $key = $AGI->stream_file('pound', $LISTKEYS) if ($key == 0);
 return($key);
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_main_menu
 #                                                                          #
 # Play the 'main' menu                                                     #
 #                                                                          #
 {
 my $key = $AGI->stream_file('vm-onefor', $MAINKEYS) if ($key == 0);
 #$key = $AGI->stream_file('?????', $MAINKEYS) if ($key == 0);
 $key = play_text("a list of new messages.", $MAINKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-press', $MAINKEYS) if ($key == 0);
 $key = $AGI->stream_file('digits/2', $MAINKEYS) if ($key == 0);
 $key = $AGI->stream_file('for', $MAINKEYS) if ($key == 0);
 #$key = $AGI->stream_file('?????', $MAINKEYS) if ($key == 0);
 $key = play_text("a list of all messages.", $MAINKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-press', $MAINKEYS) if ($key == 0);
 $key = $AGI->stream_file('digits/3', $MAINKEYS) if ($key == 0);
 $key = $AGI->stream_file('for', $MAINKEYS) if ($key == 0);
 #$key = $AGI->stream_file('?????', $MAINKEYS) if ($key == 0);
 $key = play_text("a specific message", $MAINKEYS) if ($key == 0);

 $key = $AGI->stream_file('to-hang-up', $MAINKEYS) if ($key == 0);
 $key = $AGI->stream_file('vm-press', $MAINKEYS) if ($key == 0);
 $key = $AGI->stream_file('pound', $MAINKEYS) if ($key == 0);
 return($key);
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_msg_body
 #                                                                          #
 # Plays just the mesesage body                                             #
 #                                                                          #
 {
 my ($msg) = @_;
 my $key;

 $key = play_msg_body_content($msg, $BODYKEYS);

 while (1)
   {
   while ($key == 0)
     {
     $key = play_msg_body_menu();
     $key = $AGI->wait_for_digit(10) if ($key == 0);
     }

   if (($key == $THREE) ~124~~124~ ($key == $FOUR) ~124~~124~ ($key == $SIX) ~124~~124~ ($key == $SEVEN))
     {
     return($key);
     }
   elsif ($key == $FIVE)
     {
     $key = play_msg_body_content($msg, $BODYKEYS);
     next;
     }
   elsif ($key == $NINE)
     {
     my @m = ($msg);
     $IMAP->unset_flag("Seen", @m);
     $IMAP->stream_file('vm-saved', '""');
     }
   elsif ($key == $STAR)
     {
     return(0);
     }
   elsif ($key == $POUND)
     {
     hangup();
     }
   else
     {
     $AGI->verbose('PANIC [#2] - ' . $key . '!!!',  1) if ($DEBUG);
     $key = 0;
     }
   }

 # Only returns via $STAR option
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_msg_body2
 #                                                                          #
 # Plays just the mesesage body (for a specific message)                    #
 #                                                                          #
 {
 my ($msg, $key) = @_;

 $key = play_msg_body_content($msg, $AMSGKEYS) if ($key == 0);

 while (1)
   {
   while ($key == 0)
     {
     $key = play_msg_body_menu2();
     $key = $AGI->wait_for_digit(10) if ($key == 0);
     }

   if ($key == $THREE)
     {
     $key = play_msg_header($msg, 0, $AMSGKEYS);
     }
   elsif ($key == $FIVE)
     {
     $key = play_msg_body_content($msg, $AMSGKEYS);
     }
   elsif ($key == $SEVEN)
     {
     my @m = ($msg);
     $IMAP->delete_message(@m);
     $IMAP->stream_file('vm-deleted', '""');
     $key = 0;
     }
   elsif ($key == $NINE)
     {
     my @m = ($msg);
     $IMAP->unset_flag("Seen", @m);
     $IMAP->stream_file('vm-saved', '""');
     $key = 0;
     }
   elsif ($key == $STAR)
     {
     return(0);
     }
   elsif ($key == $POUND)
     {
     hangup();
     }
   else
     {
     $AGI->verbose('PANIC [#3] - ' . $key . '!!!',  1) if ($DEBUG);
     $key = 0;
     }
   }

 # Only returns via $STAR option
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_msg_body_content
 #                                                                          #
 # Plays the actual text of the selected message body                       #
 #                                                                          #
 {
 my ($msg, $listenfor) = @_;

 my $msgtxt;

 $msgtxt = $IMAP->message_string($msg) or $msgtxt = "~94~";

 if ($msgtxt eq "~94~")
   {
   $IMAP->verbose("Unable to find msg text (" . $! . ")", 1) if ($DEBUG);
   $msgtxt = "Unable to find message text!";
   }
 elsif ($msgtxt eq "")
   {
   $IMAP->verbose("Empty message", 4) if ($DEBUG);
   $msgtxt = "Message has no text!";
   }
 else
   {
   $key = $AGI->stream_file('one-moment-please', $listenfor);
   $msgtxt = parse_message_text($msgtxt);
   }

 $key = play_text($msgtxt, $listenfor) if ($key == 0);
 return($key);
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_msg_body_menu
 #                                                                          #
 # Play the menu while viewing the msg body                                 #
 #                                                                          #
 {
 my $key = $AGI->stream_file('vm-repeat', $BODYKEYS);

 $key = $AGI->stream_file('vm-delete', $AMSGKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-press', $BODYKEYS) if ($key == 0);
 $key = $AGI->stream_file('digits/9', $BODYKEYS) if ($key == 0);
 $key = $AGI->stream_file('to', $BODYKEYS) if ($key == 0);
 #$key = $AGI->stream_file('?????', $BODYKEYS) if ($key == 0);
 $key = play_text("mark message as unread", $BODYKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-press', $BODYKEYS) if ($key == 0);
 $key = $AGI->stream_file('vm-star', $BODYKEYS) if ($key == 0);
 $key = $AGI->stream_file('vm-for', $BODYKEYS) if ($key == 0);
 $key = $AGI->stream_file('list', $BODYKEYS) if ($key == 0);

 $key = $AGI->stream_file('to-hang-up', $BODYKEYS) if ($key == 0);
 $key = $AGI->stream_file('vm-press', $BODYKEYS) if ($key == 0);
 $key = $AGI->stream_file('pound', $BODYKEYS) if ($key == 0);
 return($key);
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_msg_body_menu2
 #                                                                          #
 # Play the menu while viewing the msg body (selected msg context)          #
 #                                                                          #
 {
 my $key = $AGI->stream_file('vm-press', $AMSGKEYS);
 $key = $AGI->stream_file('digits/3', $AMSGKEYS) if ($key == 0);
 $key = $AGI->stream_file('to-hear-msg-envelope', $AMSGKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-repeat', $AMSGKEYS);

 $key = $AGI->stream_file('vm-delete', $AMSGKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-press', $AMSGKEYS) if ($key == 0);
 $key = $AGI->stream_file('digits/9', $AMSGKEYS) if ($key == 0);
 $key = $AGI->stream_file('to', $AMSGKEYS) if ($key == 0);
 #$key = $AGI->stream_file('?????', $AMSGKEYS) if ($key == 0);
 $key = play_text("mark message as unread", $AMSGKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-starmain', $AMSGKEYS) if ($key == 0);

 $key = $AGI->stream_file('to-hang-up', $AMSGKEYS) if ($key == 0);
 $key = $AGI->stream_file('vm-press', $AMSGKEYS) if ($key == 0);
 $key = $AGI->stream_file('pound', $AMSGKEYS) if ($key == 0);
 return($key);
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_msg_header
 #                                                                          #
 # Plays just the mesesage header                                           #
 #                                                                          #
 {
 my ($msg, $new, $listenfor) = @_;

 my $key;

 my $from = $IMAP->get_header($msg, 'From');
 my $date = $IMAP->get_header($msg, 'Date');
 my $subj = $IMAP->get_header($msg, 'Subject');


 if ($from =~ m~124~\W+\"*\w+\<~124~)
   {
   $from =~ s~124~~94~\w*\"*(~94~\<)+\<*.*$~124~$1~124~;
   $from =~ s~124~"~124~~124~sg;                    # " Fixup colorizers
   }
 else
   {
   $from =~ s~124~~94~.*?\<(~94~\>)\>.*$~124~$1~124~;
   }

 $date =~ s~124~~94~\S+,*(.*?)$~124~$1~124~s;          # Strip DOW name, if present
 $date =~ s~124~:~124~ ~124~sg;                     # remove colons from time

 my @dt = split(' ', $date);
 $dt[1] = $MONTHV{$dt[1]};

 my $mtime = POSIX::mktime($dt[5], $dt[4], $dt[3], $dt[0], $dt[1], ($dt[2] - 1900));
 my $ctime = time();
 my @ltime = localtime($ctime);

 my $lag = $ltime[0] + (60 * $ltime[1]) + (3600 * $ltime[2]);
 my $lag2 = ($ltime[6] * $ONEDAY) + $lag;

 if (($ctime - $lag) <= $mtime)
   {
   $when = 'today';
   }
 elsif ((($ctime - $lag) - $ONEDAY) <= $mtime)
   {
   $when = 'yesterday';
   }
 elsif (($ctime - $lag2) <= $mtime)
   {
   my @ztime = localtime($mtime);
   $when = $DAYN[$ztime[6]];
   }
 else
   {
   $when = $MONTHN[$dt[1]] . ' ' . $dt[0] . ', ' . $dt[2];
   }

 $when .= ' at ' . $dt[3] . ':' . $dt[4];

 my $txt = "From: " . $from . "  on " . $when . '.  Subject: ' . $subj . ".";
 $key = $AGI->stream_file('vm-message', $listenfor);
 $key = $AGI->stream_file('number', $listenfor);
 $key = $AGI->say_number($msg, $listenfor) if ($key == 0);

 $key = $AGI->wait_for_digit(.1) if ($key == 0);

 $key = play_text($txt, $listenfor) if ($key == 0);
 $key = $AGI->wait_for_digit(.1) if ($key == 0);
 return($key);
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_text
 #                                                                          #
 # Cloned from festival-play.pl - play a text string                        #
 #                                                                          #
 {
 my ($text, $listenfor) = @_;

 my $hash = md5_hex($text);
 my $wavefile = "$SOUNDTMP/tts-$hash.wav";

 open(fileOUT, ">$SOUNDTMP/say-text-$hash.txt");
 print fileOUT "$text";
 close(fileOUT);

 my $execf = $T2WP . "text2wave $SOUNDTMP/say-text-$hash.txt -F 8000 -o $wavefile";
 system($execf);
 unlink($SOUNDTMP ."/say-text-$hash.txt");

 my $key = $AGI->stream_file('tts/'.basename($wavefile,".wav"),$listenfor);
 return($key);
 }


 # Please forgive any Perl->Wiki conversions I've missed.  I THINK this page shows the code correctly (finally).

  1. !/usr/bin/perl

  1. Added by Suretec Systems Ltd. - http://www.suretecsystems.com - 28/04/2006
use warnings;
use strict;



 use Asterisk::AGI;
 use File::Basename;
 use Mail::IMAPClient;
 use MIME::Parser;
 use Digest::MD5 qw(md5_hex);
 use POSIX;

 my $DEBUG    = 1;
 my $T2WP     = "/usr/bin/";            # path to text2wave(1) binary
 my $SOUNDDIR = '/var/lib/asterisk/sounds';
 my $SOUNDTMP = $SOUNDDIR . '/tts';

 my $ZERO =   ord('0');                 # ASCII codes?
 my $ONE =    ord('1');                 # Give me a break!
 my $TWO =    ord('2');
 my $THREE =  ord('3');
 my $FOUR =   ord('4');
 my $FIVE =   ord('5');
 my $SIX =    ord('6');
 my $SEVEN =  ord('7');
 my $EIGHT =  ord('8');
 my $NINE =   ord('9');
 my $STAR =   ord('*');
 my $POUND =  ord('#');

 my $MAINKEYS = '123#';                 # keys recognized by main menu
 my $LISTKEYS = '34567*#';              # keys recognized by list menu
 my $BODYKEYS = '345679*#';             # .. by play msg body
 my $AMSGKEYS = '3579*#';               # .. when playing a selected msg

 my %MONTHV = ( Jan => 0, Feb => 1,  'Mar' => 2,
                Apr => 3, May => 4,  'Jun' => 5,
               Jul => 6, Aug => 7,  'Sep' => 8,
               Oct => 9, Nov => 10, 'Dec' => 11  );

 my @MONTHN = ( 'January', 'February', 'March', 'April', 'May', 'June',
                'July', 'August', 'September', 'October', 'November', 'December');

 my @DAYN   = ( 'Sunday', 'Monday', 'Tuesday',
                'Wednesday', 'Thursday', 'Friday', 'Saturday');

 my $ONEDAY = (60 * 60) * 24;

 #-----------------------------------------------------------------------------
 # Notes:  must call with username, password, imap server                    #
 #-----------------------------------------------------------------------------

 die "Usage: $0 user&pass&server" if ($#ARGV != 0);

 my @auth = split('&', $ARGV[0]);
 die "Usage: $0 user&pass&server" if ($#auth != 2);

 my $AGI  = new Asterisk::AGI;
 my %input = $AGI->ReadParse();

 $AGI->setcallback(\&myExit);           # Hangup/Error detection

 my $IMAP = Mail::IMAPClient->new(
            User    => $auth[0],
            Password => $auth[1],
            Server  => $auth[2]);

 if (! $IMAP->login)
   {
   $AGI->verbose("Unable to login ($auth[0])") if ($DEBUG);
   #$AGI->stream_file('?????', '""');
   play_text("Sorry, I could not login to the IMAP server!");
   myExit("Unable to login ($auth[0])");
   }

 if ( ! $IMAP->select("INBOX"))
   {
   $AGI->verbose("Unable to select INBOX", 1) if ($DEBUG);
   #$AGI->stream_file('?????', '""');
   play_text("Sorry, I could not find your inbox!");
   myExit("Unable to select Inbox");
   }

 $IMAP->Peek(1) if ($DEBUG);

 my %newMSGs;

 my $newmsgcnt = 0;
 my @seen   = $IMAP->seen;
 my @all    = $IMAP->messages;
 my $msgcnt = $#all;

 %hseen = ();
 foreach $_ (@seen)
   {
   $hseen{$_} = 1;
   }

 foreach $msg (@all)
   {
   if ( ! exists($hseen{$msg}))
     {
     $newMSGs{$msg} = 1;
     $newmsgcnt++;
     }
   }

 my $key = $AGI->stream_file('vm-youhave', $MAINKEYS);

 if ($newmsgcnt == 0)
   {
   $key = $AGI->stream_file('no', $MAINKEYS) if ($key == 0);
   }
 else
   {
   $key = $AGI->say_number($newmsgcnt, $MAINKEYS) if ($key == 0);
   }

 $key = $AGI->stream_file('new', $MAINKEYS) if ($key == 0);
 $key = $AGI->stream_file((($newmsgcnt == 1) ? 'vm-message' : 'vm-messages'), $MAINKEYS) if ($key == 0);

 sleep(1) if ($key == 0);

 main_menu($key);  # Never returns..
 myExit("Mission Improbable!");

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub find_a_msg
 #                                                                          #
 # User wants to read a single message by #; find out what number!          #
 #                                                                          #
 {
 my $number ="";

 #my $key = $AGI->stream_file('?????', "0123456789#*") if ($key == 0);
 my $key = play_text("Enter the message number, followed by the pound sign", "0123456789#*");

 while ($key != $POUND)
   {
   return(0) if ($key == $STAR);
   last      if ($key == $POUND);

   $number .= $key if ($key != 0);
   $AGI->wait_for_digit(7);

   if (($number eq "") && ($key == 0))
     {
     #$key = $AGI->stream_file('?????', "0123456789#*") if ($key == 0);
     $key = play_text("Enter the message number, followed by the pound sign", "0123456789#*");
     }
   else
     {
     #$key = $AGI->stream_file('?????', "0123456789#*") if ($key == 0);
     $key = play_text("You must end with the pound sign.  Push the star key to abort.");
     }
   }

 if ( ! $IMAP->get_header($number, 'Date'))
   {
   #$key = $AGI->stream_file('?????', '""');
   play_text("Sorry, message number " . $number . " could not be located.");
   sleep(1);
   return(0);
   }

 $key = play_number_header($number, 0, $AMSGKEYS);
 $key = play_number_body2($number, $key);
 return(0);
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub hangup
 #                                                                           #
 # User hit '#', end the session.                                            #
 #                                                                           #
 {
 $AGI->stream_file('goodbye', '""');
 $AGI->hangup();
 myExit();
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub list_messages
 #                                                                          #
 # Sequentially play each new message (newest first)                        #
 #                                                                          #
 {
 my ($new) = @_;                                # are we considering only 'unseen'?
 my $key = 0;

 if (($new) && ($newmsgcnt < 1))
   {
   $key = $AGI->stream_file('vm-youhave', $MAINKEYS);
   $key = $AGI->stream_file('no', $MAINKEYS) if ($key == 0);
   $key = $AGI->stream_file('new', $MAINKEYS) if ($key == 0);
   $key = $AGI->stream_file('vm-messages', $MAINKEYS) if ($key == 0);
   return($key);
   }

 for ($i=$msgcnt; $i >=0; $i--)
   {
   $msg = $all[$i];

   next if (($new) && (! defined $newMSGs{$msg}));

   # Note that "$key < 0" below does NOT imply 'hungup or error'.
   # Rather, it's part of a kludge to pass keys through from the submenu

   $key = play_msg_header($msg, $new, $LISTKEYS) unless ($key < 0);

   $key = 0 - $key if ($key < 0) ;
   $key = 0 if ($key == $EIGHT);                # kludge to skip hdr on return from body

   while ($key == 0)
     {
     $key = play_list_menu();
     $key = $AGI->wait_for_digit(10) if ($key == 0);
     }

   if ($key != 0)
     {
     if ($key == $THREE)                        # Repeat current hdr
       {
       $i++; next;                      # (Loop offsets increment)
       }
     elsif ($key == $FOUR)              # Play prev (newer) message
       {
       my $newmsg = -1;
                                        # this is fairly ugly...
       if ($i < $msgcnt)
         {
         if ($new)                      # (find prev 'new' message)
           {
          for $j ($i+1 .. $msgcnt)
            {
            if (defined $newMSGs{$all[$j]})
              {
              $newmsg = $j;
              last;
              }
            }
          }
         else                           # (or select prev 'any' message)
           {
          $newmsg = $i + 1;
           }
        }

       if ($newmsg < 0)
         {
        $key = $AGI->stream_file('vm-nomore', $LISTKEYS);
        }
       else
         {
        $i = $newmsg + 1;               # (account for loop decrement)
        next;
        }
       }
     elsif ($key == $FIVE)              # Play message body for this message
       {
       $key = play_msg_body($msg);

       if ($key != $THREE)              # (key passthrough kludge)
          {
          $key = ($key > 0) ? (0 - $key) : (0 - $EIGHT);
         }
       next;
       }
     elsif ($key == $SIX)               # Play next (older) message
       {
       my $newmsg = -1;

       if ($i > 0)
         {
         if ($new)                      # (find next 'new' message)
           {
           for ($j = $i-1; $j >= 0; $j--)
            {
            if (defined $newMSGs{$all[$j]})
              {
              $newmsg = $j;
              last;
              }
            }
          }
        else
           {
           $newmsg = $i - 1;
          }
        }

       if ($newmsg < 0)
         {
        $key = $AGI->stream_file('vm-nomore', $LISTKEYS);
        }
       else
         {
        $i = $newmsg + 1;               # (account for loop decrement)
        next;
        }
       }
     elsif ($key == $SEVEN)             # Delete message
       {
       my @m = ($msg);
       my $c = $IMAP->delete_message(@m);
       if (($DEBUG) && ($c != 1))
         {
        $AGI->verbose("delete_messge returned: " . $c, 1) if ($DEBUG);
        }
       $IMAP->stream_file('vm-deleted', '""');
       }
     elsif ($key == $STAR) { return(0); }
     elsif ($key == $POUND) { hangup(); }
     else
       {
       $AGI->verbose('PANIC [#1] - ' . $key . '!!!',  1) if ($DEBUG);
       $key = 0;
       }
     }
   }

 return(0);             # non-executable?
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub main_menu
 #                                                                          #
 # Play and interpret the main menu                                         #
 #                                                                          #
 {
 my ($key) = @_;

 while (1)
   {
   while ($key == 0)
     {
     $key = play_main_menu();
     $key = $AGI->wait_for_digit(10) if ($key == 0);
     }

   if ($key == $ONE)      { $key = list_messages(1); }
   elsif ($key == $TWO)   { $key = list_messages(0); }
   elsif ($key == $THREE) { $key = find_a_msg(); }
   elsif ($key == $POUND)
     {
     hangup();
     }
   else
    {
    $AGI->verbose('PANIC [#0] - ' . $key . '!!!',  1) if ($DEBUG);
    $key = 0;
    }
   # Note: INVALID keys are not passed through from stream_file()
   }

 # Only exits via hangup() option
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub myExit
 #                                                                          #
 # Terminate w/ cleanup                                                     #
 #                                                                          #
 {
 ($msg) = @_;

 $IMAP->close;

 if ($msg != '')
   {
   $AGI->verbose("Exited: " . $msg) if ($DEBUG);
   die $msg;
   }
 exit;
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub parse_message_text
 #                                                                          #
 # Find something in the message we can 'read' to the user                  #
 #                                                                          #
 {
 my ($msgtxt) = @_;

 my $newtxt = '';
 my $parser =  new MIME::Parser;

 $parser->output_under('/tmp');
 $parser->decode_headers(1);
 $parser->extract_nested_messages(0);
 $parser->ignore_errors(1);

 my $entity = $parser->parse_data($msgtxt);

 if ($entity->bodyhandle)
   {
   $newtxt = $entity->bodyhandle->as_string;
   }
 elsif ($entity->parts > -1)
   {
   $newtxt = $entity->parts(0);
   }
 else
   {
   $newtxt = "Unable to parse message text!";
   }

 return($newtxt);
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_list_menu
 #                                                                          #
 # Play the 'listing messages' menu                                         #
 #                                                                          #
 {
 my $key = $AGI->stream_file('vm-press', $LISTKEYS);
 $key = $AGI->stream_file('digits/3', $LISTKEYS) if ($key == 0);
 $key = $AGI->stream_file('to-hear-msg-envelope', $LISTKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-prev', $LISTKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-press', $LISTKEYS) if ($key == 0);
 $key = $AGI->stream_file('digits/5', $LISTKEYS) if ($key == 0);
 $key = $AGI->stream_file('to-listen-to-it', $LISTKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-next', $LISTKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-starmain', $LISTKEYS) if ($key == 0);

 $key = $AGI->stream_file('to-hang-up', $LISTKEYS) if ($key == 0);
 $key = $AGI->stream_file('vm-press', $LISTKEYS) if ($key == 0);
 $key = $AGI->stream_file('pound', $LISTKEYS) if ($key == 0);
 return($key);
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_main_menu
 #                                                                          #
 # Play the 'main' menu                                                     #
 #                                                                          #
 {
 my $key = $AGI->stream_file('vm-onefor', $MAINKEYS) if ($key == 0);
 #$key = $AGI->stream_file('?????', $MAINKEYS) if ($key == 0);
 $key = play_text("a list of new messages.", $MAINKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-press', $MAINKEYS) if ($key == 0);
 $key = $AGI->stream_file('digits/2', $MAINKEYS) if ($key == 0);
 $key = $AGI->stream_file('for', $MAINKEYS) if ($key == 0);
 #$key = $AGI->stream_file('?????', $MAINKEYS) if ($key == 0);
 $key = play_text("a list of all messages.", $MAINKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-press', $MAINKEYS) if ($key == 0);
 $key = $AGI->stream_file('digits/3', $MAINKEYS) if ($key == 0);
 $key = $AGI->stream_file('for', $MAINKEYS) if ($key == 0);
 #$key = $AGI->stream_file('?????', $MAINKEYS) if ($key == 0);
 $key = play_text("a specific message", $MAINKEYS) if ($key == 0);

 $key = $AGI->stream_file('to-hang-up', $MAINKEYS) if ($key == 0);
 $key = $AGI->stream_file('vm-press', $MAINKEYS) if ($key == 0);
 $key = $AGI->stream_file('pound', $MAINKEYS) if ($key == 0);
 return($key);
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_msg_body
 #                                                                          #
 # Plays just the mesesage body                                             #
 #                                                                          #
 {
 my ($msg) = @_;
 my $key;

 $key = play_msg_body_content($msg, $BODYKEYS);

 while (1)
   {
   while ($key == 0)
     {
     $key = play_msg_body_menu();
     $key = $AGI->wait_for_digit(10) if ($key == 0);
     }

   if (($key == $THREE) ~124~~124~ ($key == $FOUR) ~124~~124~ ($key == $SIX) ~124~~124~ ($key == $SEVEN))
     {
     return($key);
     }
   elsif ($key == $FIVE)
     {
     $key = play_msg_body_content($msg, $BODYKEYS);
     next;
     }
   elsif ($key == $NINE)
     {
     my @m = ($msg);
     $IMAP->unset_flag("Seen", @m);
     $IMAP->stream_file('vm-saved', '""');
     }
   elsif ($key == $STAR)
     {
     return(0);
     }
   elsif ($key == $POUND)
     {
     hangup();
     }
   else
     {
     $AGI->verbose('PANIC [#2] - ' . $key . '!!!',  1) if ($DEBUG);
     $key = 0;
     }
   }

 # Only returns via $STAR option
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_msg_body2
 #                                                                          #
 # Plays just the mesesage body (for a specific message)                    #
 #                                                                          #
 {
 my ($msg, $key) = @_;

 $key = play_msg_body_content($msg, $AMSGKEYS) if ($key == 0);

 while (1)
   {
   while ($key == 0)
     {
     $key = play_msg_body_menu2();
     $key = $AGI->wait_for_digit(10) if ($key == 0);
     }

   if ($key == $THREE)
     {
     $key = play_msg_header($msg, 0, $AMSGKEYS);
     }
   elsif ($key == $FIVE)
     {
     $key = play_msg_body_content($msg, $AMSGKEYS);
     }
   elsif ($key == $SEVEN)
     {
     my @m = ($msg);
     $IMAP->delete_message(@m);
     $IMAP->stream_file('vm-deleted', '""');
     $key = 0;
     }
   elsif ($key == $NINE)
     {
     my @m = ($msg);
     $IMAP->unset_flag("Seen", @m);
     $IMAP->stream_file('vm-saved', '""');
     $key = 0;
     }
   elsif ($key == $STAR)
     {
     return(0);
     }
   elsif ($key == $POUND)
     {
     hangup();
     }
   else
     {
     $AGI->verbose('PANIC [#3] - ' . $key . '!!!',  1) if ($DEBUG);
     $key = 0;
     }
   }

 # Only returns via $STAR option
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_msg_body_content
 #                                                                          #
 # Plays the actual text of the selected message body                       #
 #                                                                          #
 {
 my ($msg, $listenfor) = @_;

 my $msgtxt;

 $msgtxt = $IMAP->message_string($msg) or $msgtxt = "~94~";

 if ($msgtxt eq "~94~")
   {
   $IMAP->verbose("Unable to find msg text (" . $! . ")", 1) if ($DEBUG);
   $msgtxt = "Unable to find message text!";
   }
 elsif ($msgtxt eq "")
   {
   $IMAP->verbose("Empty message", 4) if ($DEBUG);
   $msgtxt = "Message has no text!";
   }
 else
   {
   $key = $AGI->stream_file('one-moment-please', $listenfor);
   $msgtxt = parse_message_text($msgtxt);
   }

 $key = play_text($msgtxt, $listenfor) if ($key == 0);
 return($key);
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_msg_body_menu
 #                                                                          #
 # Play the menu while viewing the msg body                                 #
 #                                                                          #
 {
 my $key = $AGI->stream_file('vm-repeat', $BODYKEYS);

 $key = $AGI->stream_file('vm-delete', $AMSGKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-press', $BODYKEYS) if ($key == 0);
 $key = $AGI->stream_file('digits/9', $BODYKEYS) if ($key == 0);
 $key = $AGI->stream_file('to', $BODYKEYS) if ($key == 0);
 #$key = $AGI->stream_file('?????', $BODYKEYS) if ($key == 0);
 $key = play_text("mark message as unread", $BODYKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-press', $BODYKEYS) if ($key == 0);
 $key = $AGI->stream_file('vm-star', $BODYKEYS) if ($key == 0);
 $key = $AGI->stream_file('vm-for', $BODYKEYS) if ($key == 0);
 $key = $AGI->stream_file('list', $BODYKEYS) if ($key == 0);

 $key = $AGI->stream_file('to-hang-up', $BODYKEYS) if ($key == 0);
 $key = $AGI->stream_file('vm-press', $BODYKEYS) if ($key == 0);
 $key = $AGI->stream_file('pound', $BODYKEYS) if ($key == 0);
 return($key);
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_msg_body_menu2
 #                                                                          #
 # Play the menu while viewing the msg body (selected msg context)          #
 #                                                                          #
 {
 my $key = $AGI->stream_file('vm-press', $AMSGKEYS);
 $key = $AGI->stream_file('digits/3', $AMSGKEYS) if ($key == 0);
 $key = $AGI->stream_file('to-hear-msg-envelope', $AMSGKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-repeat', $AMSGKEYS);

 $key = $AGI->stream_file('vm-delete', $AMSGKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-press', $AMSGKEYS) if ($key == 0);
 $key = $AGI->stream_file('digits/9', $AMSGKEYS) if ($key == 0);
 $key = $AGI->stream_file('to', $AMSGKEYS) if ($key == 0);
 #$key = $AGI->stream_file('?????', $AMSGKEYS) if ($key == 0);
 $key = play_text("mark message as unread", $AMSGKEYS) if ($key == 0);

 $key = $AGI->stream_file('vm-starmain', $AMSGKEYS) if ($key == 0);

 $key = $AGI->stream_file('to-hang-up', $AMSGKEYS) if ($key == 0);
 $key = $AGI->stream_file('vm-press', $AMSGKEYS) if ($key == 0);
 $key = $AGI->stream_file('pound', $AMSGKEYS) if ($key == 0);
 return($key);
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_msg_header
 #                                                                          #
 # Plays just the mesesage header                                           #
 #                                                                          #
 {
 my ($msg, $new, $listenfor) = @_;

 my $key;

 my $from = $IMAP->get_header($msg, 'From');
 my $date = $IMAP->get_header($msg, 'Date');
 my $subj = $IMAP->get_header($msg, 'Subject');


 if ($from =~ m~124~\W+\"*\w+\<~124~)
   {
   $from =~ s~124~~94~\w*\"*(~94~\<)+\<*.*$~124~$1~124~;
   $from =~ s~124~"~124~~124~sg;                    # " Fixup colorizers
   }
 else
   {
   $from =~ s~124~~94~.*?\<(~94~\>)\>.*$~124~$1~124~;
   }

 $date =~ s~124~~94~\S+,*(.*?)$~124~$1~124~s;          # Strip DOW name, if present
 $date =~ s~124~:~124~ ~124~sg;                     # remove colons from time

 my @dt = split(' ', $date);
 $dt[1] = $MONTHV{$dt[1]};

 my $mtime = POSIX::mktime($dt[5], $dt[4], $dt[3], $dt[0], $dt[1], ($dt[2] - 1900));
 my $ctime = time();
 my @ltime = localtime($ctime);

 my $lag = $ltime[0] + (60 * $ltime[1]) + (3600 * $ltime[2]);
 my $lag2 = ($ltime[6] * $ONEDAY) + $lag;

 if (($ctime - $lag) <= $mtime)
   {
   $when = 'today';
   }
 elsif ((($ctime - $lag) - $ONEDAY) <= $mtime)
   {
   $when = 'yesterday';
   }
 elsif (($ctime - $lag2) <= $mtime)
   {
   my @ztime = localtime($mtime);
   $when = $DAYN[$ztime[6]];
   }
 else
   {
   $when = $MONTHN[$dt[1]] . ' ' . $dt[0] . ', ' . $dt[2];
   }

 $when .= ' at ' . $dt[3] . ':' . $dt[4];

 my $txt = "From: " . $from . "  on " . $when . '.  Subject: ' . $subj . ".";
 $key = $AGI->stream_file('vm-message', $listenfor);
 $key = $AGI->stream_file('number', $listenfor);
 $key = $AGI->say_number($msg, $listenfor) if ($key == 0);

 $key = $AGI->wait_for_digit(.1) if ($key == 0);

 $key = play_text($txt, $listenfor) if ($key == 0);
 $key = $AGI->wait_for_digit(.1) if ($key == 0);
 return($key);
 }

 # - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

 sub play_text
 #                                                                          #
 # Cloned from festival-play.pl - play a text string                        #
 #                                                                          #
 {
 my ($text, $listenfor) = @_;

 my $hash = md5_hex($text);
 my $wavefile = "$SOUNDTMP/tts-$hash.wav";

 open(fileOUT, ">$SOUNDTMP/say-text-$hash.txt");
 print fileOUT "$text";
 close(fileOUT);

 my $execf = $T2WP . "text2wave $SOUNDTMP/say-text-$hash.txt -F 8000 -o $wavefile";
 system($execf);
 unlink($SOUNDTMP ."/say-text-$hash.txt");

 my $key = $AGI->stream_file('tts/'.basename($wavefile,".wav"),$listenfor);
 return($key);
 }


 # Please forgive any Perl->Wiki conversions I've missed.  I THINK this page shows the code correctly (finally).

Created by: wcdw, Last modification: Mon 23 of Apr, 2012 (23:37 UTC) by admin
Please update this page with new information, just login and click on the "Edit" or "Discussion" tab. Get a free login here: Register Thanks! - Find us on Google+