Forums

Linking dropdown user to dynamic email

brinkruaan 05 Nov, 2009
Hi All.

I have searched for 2days now but can't seem to get what I am looking for in the forum.

My Situation 1:
We have one Intranet with 4 major different businesses with their respective departments and department heads. I have created a few forms, people use to either order Hardware,Software or new user application etc.
I have created the departments heads in a dropdown box, so when I for example want to order something,I want to be able to click on my D/Head and the email needs to be sent to my department head for approval, get my drift?

Now where exactly to I specify there emails? I would naturally(I think) use "dynamic to" in the email settings.

2: Would it be possible when the department head receive the email to have a radio button that says for example "approve" or "decline" and then be sent to the Finance Manager for final approvement (this is just the way we work, cause of strict budgets)

Any help would be much appreciated.
nml375 05 Nov, 2009
Hi,
The first part is pretty much covered by the #33 FAQ. You could use the dynamic to as well, I suppose, although that would reveal the recipient email addresses to the user (in this case, simply set the value of each option to the department email address, then enter the form field name of the dropdown into the dynamic to control in your form email setup).

As for the second part, this could be accomplished with a little creative coding. The cleanest approach would probably be to store the submitted data in a database table, and use the "extra code" to retieve this data and email it again ("forward") to the proper destination, then you'd "only" have to include an url to the form with a few extra url-encoded formdata in the original email..
There's probably quite a few other ways of doing this as well, I suppose, just the first thing that comes into my mind for this.
I'll see if I can' build a small demo once I get back on my workstation...

/Fredrik
GreyHead 05 Nov, 2009
Hi brinkruaan,

Here's an example I developed earlier this week. This code goes in the OnSubmit Before box, the form returns a value for 'radio1' and there is a Dynamic To in the Email Setup with email_to_use in the box. Change the field names and array values as required.
<?php
$radio0 = JRequest::getString('radio0', 'admin', 'post');
$emails = array (
  'accounts' => 'accounts@example.com',
  'technical' => 'technical@example.com',
  'sales' => 'sales@example.com',
  'admin' => 'admin@example.com'
);
$email_to_use = $emails[$radio0];
JRequest::setVar('email_to_use', $email_to_use);
?>


For the second part - as Fredrik suggests - it quite easy to set up links with parameters in them to mark a record as approved or disapproved and then send off another e-mail. I'd probably use a second form for that but the extra code boxes would work as well.

Bob


Bob
nml375 05 Nov, 2009
Hi,
I've got the part-2 demo done now. I'm going with the assumption that you've used Bob's solution for your email recipients;

First off, we'll need a working DB Connection. That has been covered in the tutorials, as well as multiple threads here on the forum. We'll need to store all submitted fields, as well as the cf_id primary key and the uid identifier (used for validation). Important: Also make sure that the "Saving Data/Emails order" is set to 'Before Email'.

Next, we have to move over to the Form Code tab, and access the "Extra code 1:" section. This part should handle the final processing of the email, and remove the entry from the database (to avoid multiple approvals, etc). The code should look something like this:
<?
/* Get our JTable object, makes everything a lot easier...
 * Since the DB Connection is enabled, we do not have to bother with loading the code ourselves
 */
$request =& JTable::getInstance("chronoforms_requestForm", "Table");

/* Try to load the record, and validate the 'uid', bail out if either fails */
if (!$request->load(JRequest::getVar('record', 0, 'get')) || $request->uid != JRequest::getVar('uid', '', 'get')) {
  echo "Access Denied!";
  return;
}

/* Retrieve the 'approve' field, and see if it's 'yes' or not... */
if (JRequest::getVar('approve', 'no', 'get') == 'yes') {
/* The request was approved, Build the email body using the values we stored
 * in the database. In my form, I had two fields, department and request, you 
 * probably have to adjust this part to suite your design layout.
 */
  $email = sprintf('Department: %s<br />
Request: %s',
    $request->department,
    $request->request);

/* Now use the JUtility::sendMail() method to send the mail,
 * I choose to hardcode both sender, recipient, and subject
 * in this example, but it could be extended to perhaps use
 * the department as sender, or information from the request
 * in the message subject...
 */
  JUtility::sendMail(
   'webmaster@loehr.nu',      /* Recipient email      */
   'loehr.nu administration', /* Recipient name       */
   'webmaster@loehr.nu',      /* Sender (valid email) */
   'Request approval',        /* Email Subject        */
   $email,                    /* The email body       */
   true);                     /* True for html-email  */
}

/* Processing done, lets remove the request */
$request->delete();
?>


Next, in your email setup, you'll have to disable the editor, so that we can add some php-code to your email template. This should add the proper links to your email..
Once you've disabled the editor, you'll have to add this code to the email template:
<?
/* Start by preparing our URI.. 
 * Remember to change the "jos_chronoforms_requestForm" to whatever you named your
 * database table. You could also check the "autogenerated code" tab if you're uncertain
 */
$actions = array(
  'option' => 'com_chronocontact',
  'task' => 'extra',
  'chronoformname' => JRequest::getVar('chronoformname'),
  'record' => $MyForm->tablerow["jos_chronoforms_requestForm"]->cf_id,
  'uid' => $MyForm->tablerow["jos_chronoforms_requestForm"]->uid,
  'approve' => 'yes'
);
$formAction = JURI::getInstance();
$formAction->setQuery($formAction->buildQuery($actions));

/* Finally add the html-code for the two links Approve and Decline.
 * We use the toString() method to get the URL, and setVar() to change
 * the value of 'approve' to 'no' for the second link.
 */
?>
<p>
 <a href="<?
echo $formAction->toString();
?>">Approve</a> <a href="<?
$formAction->setVar('approve', 'no');
echo $formAction->toString();
?>">Decline</a>
</p>


Once this is done, you should have two links in your email that will link to your "extra code", which in it's turn will handle the final approval email. Feel free to ask if you find anything confusing, or just get stuck getting it working.

/Fredrik
brinkruaan 06 Nov, 2009
Ok, so now all I actually wanted was this in my HTML code:

Select the recipient you wish to contact:
<select name="email_to_use">
  <option value="ruaan@example.com">Ruaan</option>
  <option value="jcarstens@example.com">Johan C</option>
  <option value="em3">Name 3</option>
</select>
</DIV>
<DIV class=form_item   >
<DIV class="form_element cf_button" ><INPUT  type=submit value=Submit ></DIV>
<DIV class=clear > </DIV></DIV>


People can see other peoples email, no problem there.
How should I change the second solution(which nmi375 gave) for this?
nml375 06 Nov, 2009
Hi,
Adding the addresses directly into the form code, as opposite to using Bob's approach, should not affect the "part 2" code.

There might be one or two things you'll have to modify to suit your form that I overlooked while commenting the code:
[list]
  • Extra 1 code: JTable::getInstance("chronoforms_requestForm", "Table")
    chronoforms_requestForm should be chronoforms_yourformname, if you are unsure of the exact value, you'll find a similar line on the Auto Generated Code Tab.

  • Extra 1 code: $email = sprintf('.....
    This block of code is used to generate the email message body. I like using sprintf(), as it lets me keep the template apart from the php variables, although writing the variables "inline" might be easier for starters.
    Use $request->fieldname to get the different values stored in the database table.

  • Extra 1 code: JUtility::sendMail()
    This method takes a minimum of 6 arguments (there are a few other optionals, see the documentation for further details): Recipient email address, Recipient email name, Sender email address, email subject, email body, use html (true) or plaintext (false). Alter these to suit your needs.

  • Email template: $MyForm->tablerow["jos_chronoforms_requestForm"]
    jos_chronoforms_requestForm should be whatever your database table is named. If you are unsure of the exact value, you'll find a similar line on the Auto Generated Code Tab.
  • [/list]
    I believe the above list should be the minimum changes needed to get the code working...

    /Fredrik
    brinkruaan 18 Mar, 2010
    Hi Guys

    It has been a while before I got to working on my forms again.
    Have had some other projects going.
    Just want to thank you guys for giving me nice support and help, but
    as at this moment I am stuck...

    I am getting everything I want, approve, decline button.
    After talk with team we have decided that when someone click on "approve"
    it should go to a certain email and decline to another email address.

    When I get the buttons and open them, all I get is in the pics below.
    Any idea where I my code might be wrong?
    GreyHead 18 Mar, 2010
    Hi brinkruaan,

    The problem is that there is no Chronoformname in the url (or anything else) so the message is correct.

    As this is now a bit dated please cna you post the code that you are using.

    Bob
    brinkruaan 18 Mar, 2010
    HI Greyhead

    Here si my code I use, please let me know which specific detail you want to see.

    Extra code 1:
        <?
        /* Get our JTable object, makes everything a lot easier...
        * Since the DB Connection is enabled, we do not have to bother with loading the code ourselves
        */
        $request =& JTable::getInstance("chronoforms_Appraisaltest", "Table");
    
        /* Try to load the record, and validate the 'uid', bail out if either fails */
        if (!$request->load(JRequest::getVar('record', 0, 'get')) || $request->uid != JRequest::getVar('uid', '', 'get')) {
          echo "Access Denied!";
          return;
        }
    
        /* Retrieve the 'approve' field, and see if it's 'yes' or not... */
        if (JRequest::getVar('approve', 'no', 'get') == 'yes') {
        /* The request was approved, Build the email body using the values we stored
        * in the database. In my form, I had two fields, department and request, you
        * probably have to adjust this part to suite your design layout.
        */
          $email = sprintf('Select_19: %s<br />
        Request: %s',
            $request->Select_19,
            $request->request);
    
        /* Now use the JUtility::sendMail() method to send the mail,
        * I choose to hardcode both sender, recipient, and subject
        * in this example, but it could be extended to perhaps use
        * the department as sender, or information from the request
        * in the message subject...
        */
          JUtility::sendMail(
           'ruaan@rupertwines.com',      /* Recipient email      */
           'John', /* Recipient name       */
           'Support@rupwrtwines.com',      /* Sender (valid email) */
           'Request approval',        /* Email Subject        */
           $email,                    /* The email body       */
           true);                     /* True for html-email  */
        }
    
        /* Processing done, lets remove the request */
        $request->delete();
        ?>


    Email Template code:

    <?
        /* Start by preparing our URI..
        * Remember to change the "jos_chronoforms_requestForm" to whatever you named your
        * database table. You could also check the "autogenerated code" tab if you're uncertain
        */
        $actions = array(
          'option' => 'com_chronocontact',
          'task' => 'extra',
          'chronoformname' => JRequest::getVar('Appraisaltest'),
          'record' => $MyForm->tablerow["jos_chronoforms_Appraisaltest"]->cf_id,
          'uid' => $MyForm->tablerow["jos_chronoforms_Appraisaltest"]->uid,
          'approve' => 'yes'
        );
        $formAction = JURI::getInstance();
        $formAction->setQuery($formAction->buildQuery($actions));
    
        /* Finally add the html-code for the two links Approve and Decline.
        * We use the toString() method to get the URL, and setVar() to change
        * the value of 'approve' to 'no' for the second link.
        */
        ?>
        <p>
        <a href="<?
        echo $formAction->toString();
        ?>">Approve</a> <a href="<?
        $formAction->setVar('approve', 'no');
        echo $formAction->toString();
        ?>">Decline</a>
        </p>


    Thanks
    GreyHead 18 Mar, 2010
    Hi brinkruaan,

    You might find more by adding some debug code to output some of the variables.

    I think that the problem is in the email template code where you are not accessing the values from $MyForm correctly . . .

    . . . but I really can't follow the logic so I'll leave it to Fredrik.

    Bob
    brinkruaan 18 Mar, 2010
    Hi GreayHead

    Won't it be easier using something like:
    mailto:email@address.com?Subject=Approve ?
    Cause at this moment it should basicly just forward the email to the recipient.
    And if i do get that working, would it be possible ( because you are just actually fwd email)
    to restrict someone to edit the form?

    Maybe:

    <HTML>
    <HEAD>
    <TITLE>EFORM Approval</TITLE>
    </HEAD>

    <BODY>
    <H3>EForm Approval</H3>

    <FORM ACTION='mailto:email?subject=APPROVE'
    METHOD=POST ENCTYPE='text/plain'>
    <INPUT TYPE=SUBMIT VALUE='APPROVE'></FORM>
    <FORM ACTION='mailto:email?subject=DECLINE'
    METHOD=POST ENCTYPE='text/plain'>
    <INPUT TYPE=SUBMIT VALUE='DECLINE'>
    </FORM>
    </BODY>
    </HTML>

    Thanks
    nml375 18 Mar, 2010
    Hi,
    The error is in your email template code:
        $actions = array(
          'option' => 'com_chronocontact',
          'task' => 'extra',
          'chronoformname' => JRequest::getVar('Appraisaltest'),
          'record' => $MyForm->tablerow["jos_chronoforms_Appraisaltest"]->cf_id,
          'uid' => $MyForm->tablerow["jos_chronoforms_Appraisaltest"]->uid,
          'approve' => 'yes'
        );

    The key problem is 'chronoformname' => JRequest::getVar('Appraisaltest'),
    This tries to fetch the value of a form field named Appraisaltest, and the value is used as the form name for the approve/decline links. This was intended to be exactly 'chronoformname', not 'Appraisaltest'. On the other hand, since the form name is already known, this could be hardcoded - assuming you do not intend to rename the form in the future. The following should work fine, as it fetches the formname directy from the $MyForm object:
        $actions = array(
          'option' => 'com_chronocontact',
          'task' => 'extra',
          'chronoformname' => $MyForm->formname,
          'record' => $MyForm->tablerow["jos_chronoforms_Appraisaltest"]->cf_id,
          'uid' => $MyForm->tablerow["jos_chronoforms_Appraisaltest"]->uid,
          'approve' => 'yes'
        );


    Further, both record and uid are empty; Could you post the database table structure for "jos_chronoforms_Appraisaltest"? I suspect there are no cf_id or uid table fields, and these are needed to identify the correct row from the database table and validate authorization (could probably be improved to check a random hash instead of the uid).

    /Fredrik
    brinkruaan 19 Mar, 2010
    HI Frederick

    Thanks for all your help.
    Just to clear things up, here is what I am trying to achieve:

    User - fill in the form. It sends to his Dep.Head - which in his turn makes first
    approval/rejection. If approved it goes to the Financial Manager and when he Approves /rejects It will go to either IT (Approved) or Dept.H(Rejected) . the last step from FM can be done Manually, As I think it will get to complicated in the coding (for me, that is).

    DeptH > changes
    FM > Same person
    IT > same person

    Here is a pic of what we trying to do, which you probably know by now.....
    nml375 20 Mar, 2010
    Hi,
    If you simply want your Financial Manager to forward the email to either "IT" or "DH", then you don't need the extended code. You'd simply use the FAQ #31 solution to send the email to the proper Dept. Head.
    The extended code I posted would only be needed for those "accept/refuse"-buttons/links you initially asked for.

    /Fredrik
    This topic is locked and no more replies can be posted.