function readOnly(count){ }
Starting November 20, the site will be set to read-only. On December 4, 2023,
forum discussions will move to the Trailblazer Community.
+ Start a Discussion
EWEW 

Receiving "DML currently not allowed" exception

Hello all. I'm having an issue with my Visualforce controller code and was wondering if anyone had any ideas for me.

The error I'm receiving is:
Code:
System.Exception: DML currently not allowed

Class.maExtension.save: line 18, column 13
External entry point
 
My controller code is:
Code:
public class maExtension {

 public scr__c scr {get; private set;}

 public maExtension() {
  scr = new scr__c();
 }

 public pagereference save() {
  scr.market_area__c = getmarket().id;
  system.debug('Market ID: ' + scr.market_area__c);
  system.debug('First Name: ' + scr.first_name__c);
  system.debug('Last Name: ' + scr.last_name__c);
  system.debug('Full Address: ' + scr.street_1__c + 
   ' ' + scr.street_2__c + ' ' + scr.city__c + 
   ' ' + scr.state__c + ' ' + scr.zip_code__c);
  try {
   insert scr;
   system.debug('Insert Successful');
  } catch(System.DmlException e) {
   system.debug(e.getDmlMessage(0));
  }
  return null;
 }

 ma__c market;

 public string getzip() {
  string zip = apexpages.currentpage().getparameters().get('zip');
  return zip;
 }

 public string getaddress() {
  string address = apexpages.currentpage().getparameters().get('street');
  return address;
 }

 public string getcity() {
  string city = getmarket().name;
  return city;
 }

 public string getstate() {
  string state = getmarket().primary_state__c;
  return state;
 }

 public boolean getmarketexists() {
  string zip = getzip();
  integer count = [select count() 
  from ma__c 
  where primary_zip_code__c = :zip 
  limit 1];
  boolean marketexists = count > 0 ? true : false;
  return marketexists;
 }

 public boolean getmarkethascoverage() {
  string zip = getzip();
  integer count = [select count() 
  from ma__c 
  where primary_zip_code__c = :zip 
  and (status__c = 'Partial Coverage' or status__c = 'Full Coverage') 
  limit 1];
  boolean getmarkethascoverage = count > 0 ? true : false;
  return getmarkethascoverage;
 }

 public ma__c getmarket() {
  if (getmarketexists() == true) {
   string zip = getzip();
   market = [select id, name, primary_zip_code__c, primary_state__c, status__c 
   from ma__c 
   where primary_zip_code__c = :zip 
   limit 1];
  } else {
   market = new ma__c();
  }
  return market;
 }

}
 
My Visualforce Page is:
Code:
 <apex:form id="scrform">
  <apex:inputfield id="scrfirstname" value="{!scr.first_name__c}" />First Name<br />
  <apex:inputfield id="scrlastname" value="{!scr.last_name__c}" />Last Name<br />
  <apex:inputfield id="scremail" value="{!scr.email_address__c}" />Email<br />
  <apex:inputfield id="scrstreet1" value="{!scr.street_1__c}" />Street Address 1<br />
  <apex:inputfield id="scrstreet2" value="{!scr.street_2__c}" />Street Address 2<br />
  <apex:inputfield id="scrcity" value="{!scr.city__c}" />City<br />
  <apex:inputfield id="scrstate" value="{!scr.state__c}" />State<br />
  <apex:inputfield id="scrzip" value="{!scr.zip_code__c}" />Zip Code<br />
  <apex:commandbutton action="{!save}" value="Sign Me Up" /><br />
 </apex:form>

When the "Sign Me Up" button invoking the save() method is clicked, I receive the exception. Any help would be greatly appreciated. Thanks!
Best Answer chosen by Admin (Salesforce Developers) 
EWEW
Fixed it. In case anyone has this issue in the future, the "allowDML" attribute of the Visualforce component must be set to true in order for the save method to function.

All Answers

EWEW
Fixed it. In case anyone has this issue in the future, the "allowDML" attribute of the Visualforce component must be set to true in order for the save method to function.
This was selected as the best answer
Ron HessRon Hess
Yes, but your page is not in a component that i could tell.

was that form inside a component?
EWEW
Yes, the form was inside a component. I only included the form code, and not the container tags, since I didn't think it made a difference whether it was a page or a component. That'll teach me. :-)
Ron WildRon Wild
I'm getting the same error at the visualforce page level (not in a component) ... can DML calls be made from a page controller?

I don't see an "allowDML" attribute on apex:page


Ron WildRon Wild
Ah-ha! I found the answer.

DML is allowed in page controllers, but not allowed in constructors or getters & setters.  It must be invoked via an action method.

So to invoke a method using DML on page load I had to use the "action" attribute in the apex:page component:

Page:

<apex:page controller="controllerWithDML" action = "{!dmlOperation}">

</apex>
 
Controller:

public class controllerWithDML {

    public controllerWithDML() {
    }

    public PageReference dmlOperation() {
         // setup code ...
         insert sObject;
         // cleanup code ...
    }

}
 



danwilkiedanwilkie

Thanks Ron Wild, that works like a dream! :smileyvery-happy:

 

Dan 

RakeebRakeeb

HI ,i have scenario like uploading csv file and inserting into custom object,i have code here as fallow and kindly check it out and i am getting error when i am inserting the record in to custom object .Error was "System.LimitException: DML currently not allowed

Class.uploadCSVcontroller.

getResults: line 54, column 23 External entry point "let me know the sol asap

Apex:
public class uploadCSVcontroller {

        public Blob contentFile { get; set; }
        public String nameFile  { get; set; }
        public Integer rowCount { get; set; }
        public Integer colCount { get; set; }
     
      
      
        public List<List<String>> getResults() {
           
            List<List<String>> parsedCSV = new List<List<String>>();
           
          
            rowCount = 0;
            colCount = 0;
            if (contentFile != null){
                String fileString = contentFile.toString();
                parsedCSV = parseCSV(fileString, false);
                System.debug('parsedCSV:'+parsedCSV);
                rowCount = parsedCSV.size();
                System.debug('RowCount:'+rowCount);
             
                List<Sales_Claim__c> recs=new List<Sales_Claim__c>();
                Integer rowCount=0;
               
                 for (List<String> row : parsedCSV)
                  {
              
                
                   Sales_Claim__c rec=new  Sales_Claim__c();
                   System.debug('REC:'+rec);
                   recs.add(rec);
                   System.debug('recs1:'+recs);
                   for (String col : row)
                   {
                                    
                     rec.put('Quarter__c', row[0]);
                     System.debug('QA:'+row[0]);
                     rec.put('Reseller__c', row[1]);
                     rec.put('Status__c', row[2]);
                    }
                   
                     }
                    
                      insert recs;
                     System.debug('Successfull Inserted:'+recs);
  
             
                        }
            return parsedCSV;
        }

      
        public static List<List<String>> parseCSV(String contents,Boolean skipHeaders) {
            List<List<String>> allFields = new List<List<String>>();
            contents = contents.replaceAll(',"""',',"DBLQT').replaceall('""",','DBLQT",');
            //System.debug('contents:'+contents);
            contents = contents.replaceAll('""','DBLQT');
            System.debug('contents:'+contents);
            List<String> lines = new List<String>();
            try {
              
                lines = contents.split('\r'); // using carriage return accomodates windows, unix, and mac files
             
            } catch (System.ListException e) {
                System.debug('Limits exceeded?' + e.getMessage());
            }
            Integer num = 0;
            for(String line: lines) {
                // check for blank CSV lines (only commas)
                if (line.replaceAll(',','').trim().length() == 0) break;
              
                List<String> fields = line.split(',');
                List<String> cleanFields = new List<String>();
                String compositeField;
                Boolean makeCompositeField = false;
                for(String field: fields) {
                    if (field.startsWith('"') && field.endsWith('"')) {
                        cleanFields.add(field.replaceAll('DBLQT','"'));
                    } else if (field.startsWith('"')) {
                        makeCompositeField = true;
                        compositeField = field;
                    } else if (field.endsWith('"')) {
                        compositeField += ',' + field;
                        cleanFields.add(compositeField.replaceAll('DBLQT','"'));
                        makeCompositeField = false;
                    } else if (makeCompositeField) {
                        compositeField +=  ',' + field;
                    } else {
                        cleanFields.add(field.replaceAll('DBLQT','"'));
                    }
                }
              
                allFields.add(cleanFields);
            }
            if (skipHeaders) allFields.remove(0);
            System.debug('allFields:'+allFields);
            return allFields;
                
        }

    }

Page:
======
<apex:page controller="uploadCSVcontroller" >
      <apex:form >
      <apex:inputFile value="{!contentFile}" filename="{!nameFile}" /><br/>
      <apex:commandButton value="Upload" id="theButton"/>
      </apex:form>
      <apex:outputPanel id="results">
      <p>nameFile: {!nameFile}</p>
      <p>rowCount: {!rowCount}</p>
      <p>colCount: {!colCount}</p>
        <table title="CSV Output" border="1" width="100%">
           <apex:repeat value="{!results}" var="row">
               <tr>
                   <apex:repeat value="{!row}" var="cell">
                       <td> {!cell} </td>
                   </apex:repeat>
               </tr>
           </apex:repeat>
         </table>
      </apex:outputPanel>
    </apex:page>



Anthony LinzAnthony Linz
I'm a little late to the party but I want folks to know Ron Wild's suggestion also worked in my case. In the constructor I check if a record's field matches a variable and if it doesn't, i need it delete and then to insert a record where the field has the correct value. We already had an action method in the page controller so I change the action method to something called '{!callRenderMethods}'. In the controller method callRenderMethods I called the original method that was in the page controller action attribute as well as my new method that both inserts and deletes. Works exactly how I need it to. Thank you Ron.