Service and Support Blog

Service and Support Blog

Service and Support Blog - October 2008

  • How To Stop People From Making Comments On Closed Cases

    Marco Casalaina Oct 29, 2008

    Sometimes customers ask me how they can make closed cases "uncommentable" – once those cases are closed, they don't want their reps to be able to make new comments on them.

    Traditionally the way to accomplish this would be to change the record type of closed cases and use a layout for that record type which hides the Case Comments related list.  This is not ideal, though, because it means that you can't read the comments either.

    Fortunately, with Workflow From Case Comments, there is now a better way.

    As I mentioned in my previous blog entry, Workflow From Case Comments is a "chaining" workflow, which means that when it edits the parent case, it kicks off the workflow anew on that case object.  We can use this to our advantage in solving this problem.  Here's how.

    1.  Define a checkbox-type custom field on Case called "No more comments."  Do not add it to any of the Case page layouts.
    Validation1

    2.  Make a validation rule which shows the error "You cannot add comments to a closed case" at the top of the page.  In the formula section put simply "No_more_comments__c =true" (see first screenshot, left).

    3.  Make a Workflow on the Case Comments object which fires when Case: Closed equals True (see second screenshot).

    Validation2 4.  Make a Field Update in that workflow which sets the No More Comments field to true.

    5.  Activate the workflow rule!

    Now, when you try to submit a comment on a closed case, the workflow will fire on the case comment.  This will make the modification to the No More Comments field on the Case to set it to true, which will violate the validation rule and disallow the save, showing the error "You cannot add comments to a closed case." (see triumphant third screenshot)

    Validation3 Workflow From Case Comments to the rescue!

    -Marco Casalaina

  • Workflow From Case Comments!

    Marco Casalaina Oct 16, 2008

    I am pleased to report that the Winter '09 release includes a feature that customers have been asking about for years: Workflow From Case Comments!

    Shot1_3 Workflow From Case Comments gives you the ability to create a workflow rule on the Case Comments object.  From that rule, you can create a field update that takes effect on either the comment itself or on the parent case.

    This means that you can finally create those workflows you've been waiting for!

    For example, let's say I have a process whereby I set my case to a status of "Awaiting Customer Shot2 Response" when I'm waiting for the customer to get back to me.  Now my customer logs into the Customer Portal and adds a comment to the case.  That constitutes a response, so the system should automatically set my case back to a "Working" status.

    The screenshots shown here to the right document how I wrote a workflow that does just that.  All I have to do is write a workflow rule on Case Comment with the requisite criteria (and the criteria can refer to items from the Case as well).  Once that's done, I can make a field update that updates the status field on the case.

    As people begin creating workflows from Case Comments, they inevitably notice that only Field Update and Outbound Message are available from these workflow rules.  Then they ask me, what if I want to send an email?Shot3_3

    As with workflow from Email Messages, Workflow From Case Comments is a "chaining" workflow – it can trigger other workflow. Right now you can't put an email alert on the comment for the same reason you can't put a task on it: because the Comments object does not support Activities as children. However, you can put an email alert on a workflow on the parent case, and that workflow will get triggered and send out the email (and the email will be associated to the parent case, as you might expect).

    So, although you can't send an email directly from a Workflow From Case Comments, you can put an email alert on the parent case.  So, for example, you might make a Workflow From Case Comments that updates a "Last Comment" field on the parent case with the text of the most recent comment, and then make a workflow on Case which emails out that last comment to certain members of the Case Team.

    Case Teams!  A little foreshadowing there – I'll cover that new Winter '09 feature in my next dispatch.

    Don't forget, post any questions about this blog entry on the General board on developer.force.com so that the whole community can benefit from it.

    -Marco Casalaina

  • Adding A Link Button To Your CTI Adapter

    Marco Casalaina Oct 7, 2008

    Here's another question that CTI customers often ask me, particularly in the new age of Visualforce: "Can we add a button to the adapter that navigates to a link and passes it some information about the call?"

    Yes you can!  You can do it with a minor modification to your CTI adapter code.  Here's how.

    In my example, I've made an Apex page called "QuickCreate" that takes in as parameters the ANI (or caller ID) and the DNIS (the number that was dialed).  Now I'm going to make a button in the CTI adapter that links to this page, passing it the appropriate information for the active call on the line.

    In your .h file, add something like this:

    #define BUTTON_QUICK_CREATE 21

    In your Initialize() method, add this:

          
          CCTIButton pQCButton;
          pQCButton.SetLabel(L"QuickCreate");
          pQCButton.SetLongStyle(true);
          pQCButton.SetColor(COLOR_BEIGE);
          pQCButton.SetLinkURL(L"/001/e");
          UIAddButtonToAllLines(BUTTON_QUICK_CREATE,&pQCButton);

    Just after you call OnCallRinging, add this code (I left in my OnCallRinging code for context –  add everything from the CCTILine down):

          int nReturn = CCTIUserInterface::OnCallRinging(sCallObjectId, nCallType, true, bLogCall, mapInfoFields, mapAttachedData, nLineNumber);
          
          CCTILine* pLine = GetLine(nReturn);

          if (pLine) {
                CCTIButton* pQCButton = pLine->GetButton(BUTTON_QUICK_CREATE);
                if (pQCButton) {
                      pQCButton->SetLinkURL(L"/apex/QuickCreate?ANI="+mapInfoFields[KEY_ANI]+L"&DNIS="+mapInfoFields[KEY_DNIS]);
                      
                }
          }

    When the call is established, add the button to the line like this:

          listEnabledButtons.push_back(BUTTON_QUICK_CREATE);

    And that's all there is to it!  Now you'll have a button that shows up whenever a line is active which, when clicked, will navigate to your Visualforce page.

  • Kiva and the Quick Mass Close Button

    Marco Casalaina Oct 2, 2008

    From time to time in my job as product manager of Service & Support I come into contact with people who are using Salesforce.com to make a difference in the world.  One such company is Kiva

    Kiva is a microfinance non-profit that allows you to lend as little as $25 online to an entrepreneur in the developing world that needs a loan. On Kiva, you act as a banker to the poor by lending money to entrepreneurs in developing countries and then you get repaid.  Amazingly, in just 3 years, they've lent $44 million to 92,000 entrepreneurs, with an astonishing 98.5% repayment rate.

    Kiva is currently competing in the American Express Members Project, which will grant a grand prize of $1.5 million to the non-profit which garners the most votes from Amex cardmembers.  This money at Kiva could enable $30 million more loans to fund 60,000 more entrepreneurs so that they can lift themselves out of poverty.

    If you are an Amex cardmember, please click here to vote for Kiva – it really is a good cause.

    And now on to the meat of today's post:

    Kiva runs all of its customer service operations on Salesforce.com.  A few weeks ago they came to me with a request which I've heard before: they wanted a Mass Case Close button that skips the Case Close screen and just closes the cases.  This is just a twist on the Quick Case Close button that I have written about previously on this blog, so I was happy to oblige.

    The code is quite simple:

    {!REQUIRESCRIPT("/soap/ajax/13.0/connection.js")}

    var records = {!GETRECORDIDS($ObjectType.Case)};
    if (records[0] == null)
    {
    alert("Please select at least one case to close.")
    } else {
    //Get more info on the cases that were selected and generate a query out of it
    var updateRecords = [];

    //Iterate through the returned results
    for (var recordIndex=0;recordIndex<records.length;recordIndex++) {
    var caseUpdate = new sforce.SObject("Case");
    caseUpdate.Id = records[recordIndex];
    caseUpdate.Status = 'Closed';
    updateRecords.push(caseUpdate);
    }

    var result = sforce.connection.update(updateRecords);

    //handle errors here
    if (result.error) {
    alert('There was an error processing one or more cases');
    }

    //Reload the list view to show what he now owns
    parent.window.location.reload();
    }

    To add this code, go to Setup->Cases->Buttons and Links and make a new custom button called Mass Close.  Its Display Type should be set to List Button, its Behavior to Execute JavaScript, and its Content Source to OnClick JavaScript.  Paste the above code into the OnClick JavaScript field – but be sure to replace the caseUpdate.Status = 'Closed'; line with a status that is present in your org.

    Now you'll have to add this button to the Case list view.  To do
    this, go to Setup->Cases->Search Layouts.  Click Edit next to the
    Cases List View entry, and add your new button from the Available
    Buttons section to the Selected Buttons section.

    As with the Contention-Proof Accept Button, the trick here is that GETRECORDIDS call – it gets us the list of Case IDs that you selected from the list.  The rest here is simple, just put all those Case IDs into an array and set the case status fields to Closed, and call update.  Easy!

    Just imagine what other sorts of mass actions you could do with this method.  It's hard to fathom the creativity of the readers of this blog.

    And just in case you missed it: Vote for Kiva! :)