Some interesting support questions to help you customize your EvolutivoFW application.

How can I block a record from being edited based on the value of some field in that record?

The correct answer to this question is Record Access Control. This construction gives us full control over the access to a record using the workflow editor to establish the conditions.

Let's suppose you need to block editing a Potential record depending on the status "Closed". The map would look something like this:

<map>
  <originmodule>
    <originname>Potentials</originname>
  </originmodule>
  <detailview>
    <u>0</u>
    <d>0</d>
  </detailview>
  <listview>
    <u>0</u>
    <d>0</d>
  </listview>
</map>

The workflow conditions will set the conditions like this:

RAC Conditions

You may also be able to use the Archive Record Pattern for this, by assigning the records in that state to a read-only user.

But, while we were discussing the available options, we uncovered an interesting one that I wanted to share here: a Validation Map. The idea is to configure a validation that blocks the save action for the records in the state we want to block.

Let's suppose you want to block editing Document records that hold a GenDoc template unless the current user is the user assigned to the record or has administration privileges. We could think of a validation like this:

<map>
  <originmodule>
    <originname>Documents</originname>
  </originmodule>
  <fields>
    <field>
      <fieldname>template</fieldname>
      <validations>
        <validation>
          <rule>expression</rule>
          <restrictions>
          <restriction>GenDocTemplateUserRestriction</restriction>
          </restrictions>
        </validation>
      </validations>
    </field>
  </fields>
</map>

The GenDocTemplateUserRestriction would be:

<map>
<expression>if AND(current_template == '1', current_assigned_user_id != '1', current_assigned_user_id != getCurrentUserID()) then 0 else 1 end</expression>
</map>

which can be read as; if the document record we are trying to save is a template and the assigned user is not the current user or user with ID 1 (administrator) then reject the save.

There are a few things to note.

First, we are using the prefix current_. This is VERY important. The current_ prefix will use the values that are currently saved in the database for the evaluation. If we were to use the fields directly from the browser, then the current user could change the assigned user of the record, or the template check box and the validation would pass permitting the save action.

The other is less important. We are hard-coding the administrator user to the user with ID 1. Not only could this be incorrect because the administration privileges of the user with ID 1 can be changed, but also we are not letting other users with administration privileges edit the record. I leave that for an exercise to the reader.

This solution is, in my opinion, the worst of the three because the user experience is that they can edit the record but then not save it while the other two will not permit the edit at all.

How can I set all Leads with the same email to converted when one of them is converted?

Let's rephrase that question to make sure it is clear. We have a set of Leads that have the same email (or phone or some other identifier field), they are, most probably, the same person and should have been de-duplicated to avoid this situation completely but, maybe due to the permission system where many members of the sales team are working in parallel without sharing or some other business rules that may be in place, the reality is that we have a set of Lead records with the same field value. We want to detect when any of them is converted to a contact and automatically set also all the others as converted.

The obvious approach is to use a workflow. We trigger the workflow when the lead is converted and we set all the others to converted.

The first problem we have is that the converted field that is used to control the state of a Lead is an internal field, it is not exposed to the application. We cannot define a condition in the workflow system for that field. So our first step is to make that field visible to the application and workflow system.

For that, we create a manual application update change set. Go to the Application Updater module and create a new record. Fill in the author field and set the description to:

{
"operation": "massCreateFields",
"setting":
  {
   "Leads":{
   "LBL_LEAD_INFORMATION":{
       "converted": {
           "columntype": "int(11)",
           "typeofdata": "C~O",
           "uitype": "56",
           "displaytype": "2"
         }
     }
    }
  }
}

Now apply it and you will see the converted field in the leads module and we will be able to create a condition like this in the workflow system:

Leads Workflow Condition

Now that we can define a workflow to take some actions when a Lead is converted, we have to update all the records that have the same email/phone. For this task, I have thought of a few options but I am going to explain here a direct update to the database which is the easiest to implement and understand and also will be the fastest to execute.

We have a task named Execute Expression that permits us to execute any workflow expression. We have an expression function named executeSQL that permits us to execute any SQL command we want. So I created an Execute Expression that looks like this:

SQL Task

executeSQL('UPDATE vtiger_leaddetails SET converted=1 where email=?', email )

You can understand the power of this approach to do very advanced and performant database modifications with ease.

Make sure you adapt the SQL query to your needs and test carefully before putting this into production, as with any direct database update there is no going back after a mistake. You know how the phrase goes: with great power comes great responsibility. You have been warned :-)

Invitation

I hope those questions and answers stimulate your imagination and help you get more out of this amazing application. If you need any help adapting Evolutivo to your needs, contact us, we probably have solved the issue before, but even if we haven't we will be able to make Evolutivo do what you need and create another post for future readers!

Photo by Neil Thomas on Unsplash

Previous Post Next Post