The custom field support isnt very intuitive and giving these instructions to a client are really impractical. No one is going to know how to enter fields in a key/value pair except for a developer (which isnt practical). So I've whipped up a way for developers to insert their own fields into the module for selection. This then allows a module to grab the real custom fields right from salesforce and populate the dropdown with fields on the fly which would depreciate the existing "Custom Fields" area in the admin area.
So, I create a new module and a new hook that solves this problem by getting the fields right from salesforce rather than trying to hand feed them which isnt ever going to work to well without significant training to a client who is going to be using webforms and salesforce. Also I noticed that this module has no API-Connect function?! So I added one in the code (I swiped it from the salesforce_api module heh).
I'll contact the owner of this module and see if I can add some of these enhancements with my CVS account. If not, then you can use these instructions:
It's very simple to add. Simply replace the salesforcewebform_available_fields() function in salesforcewebform_fields.inc file whit the following
// available fields in SalesForce
function salesforcewebform_available_fields() {
$fields = array(
//Special Field to block Processing
0 => '--Do Not Map to SalesForce--',
);
//Define Implementation for hook_salesforcewebform_fields
$fields = array_merge($fields, module_invoke_all('salesforcewebform_fields'));
return $fields;
}
Then install this brand new module called salesforcefields that is attached to this comment.
| Comment | File | Size | Author |
|---|---|---|---|
| salesforcefields.zip | 1.98 KB | crystaldawn |
Comments
Comment #1
shawngo commentedERROR on line 75 in salesforcefields.module, contact RyanC please.Received this message because my SF Account credentials are less than Enterprise. Good to know that only Enterprise, Unlimited, and Developer accounts get API access.
Comment #2
crystaldawn commentedDoh lol. That line shouldnt even be there. It's not meant for public use, it's just something we want our clients to do internally so that I can explain to them the account types. So that line should be changed yea. I used this module for my own purposes and simply contributed it back so that others in the same boat could use it. The developer of this module is currently working on implementing it. I'm sure he'll see that and get it changed before he puts it in. BTW, that error msg can be thrown by multiple causes, not just the level of your account. It should actually say something to the effect of:
"Check login info and/or the services this account is able to use (Enterprise, Unlimited, etc). Contact Salesforce to find out why you cannot access this API."
The wording is up to the module dev.
Comment #3
capellicI would love to see this. I hear that this is how Plone does it.
Comment #4
bwoods commentedThis is great ... it appears that I'm running into a minor issue with required fields. I receive this error upon submission:
Required fields are missing: [LastName, Company]
The strange thing is that I mapped both of those fields in the Form Components area, and all of the Salesforce fields appear in the pulldown. What could I be missing here?
Comment #5
bwoods commentedI think I figured this out ... there seems to be a minor error in salesforcewebform.module in the latest dev build. It seems as if line 253 should read:
Instead of
If that's not the case, then I'm doing something wrong ...
Comment #6
obsidiandesign commented@bwoods: with the latest -dev build, the function call in the 'Additional Processing' field should have three arguments. Do you have all three listed?
@crystaldawn - I finally had a chance to work with this a bit, and it is very cool. The code you provided works for leads, I'm tweaking it to include accounts & contacts. One question:
Right below line 75 is some commented code: [code] //DrupalSalesforce::watchdog(SALESFORCE_LOG_SOME, 'Unable to establish Salesforce connection while issuing describeSObjects API call.', array(), WATCHDOG_ERROR);
}[/code]
Is this the correct error message, or does it come from somewhere else? Tentatively, I changed your line 75 text to read [code]
drupal_set_message("There was an error trying to connect to Salesforce. Check your login credentials and/or the services this account is able to use (Enterprise, Unlimited, etc). Contact Salesforce to find out why you cannot access this API.");[/code]
But I wanted to make sure that catch exception doesn't encompass other problems that should be listed in the error message.
Bryan O'Shea
Obsidian Design
Comment #7
crystaldawn commentedAt the time I was unsure what exceptions would cause this error. But over time I've found that its only for login errors and invalid permissions to use the API.
Comment #8
ravencoder commentedcrystaldawn's SalesForceFields is great. I am thinking of using this together with the current stable version SF Webform 6.x-1.2. Will the integration be easy or will I be better off using the 6.x-1.x-dev for my current site?
Comment #9
crystaldawn commentedWhat is the status of this? I am working on yet another client that has salesforce integration and I dont see this in the dev version yet. Was there a roadblock somewhere? I am getting ready to install again and it kinda sucks that I have to edit the module again since it's not rolled into at least a dev version yet :/
Comment #10
crystaldawn commentedHmmm I just DL'd the .zip file I first attached to this issue and I did find 1 bug in it. I dont ever remember putting this in it as I never use shorthand if statements because they are so cryptic. Maybe I didnt see this bug previously, but I know I dont write shorthand if statements. So this is either left over from something I copy/pasted somewhere or was introduced by someone else. I HATE shorthand. Its to unreadable. I must have missed this bug somehow. Probably wasnt using a ~username based installation at the time, I dont really remember.
This will result in "File not found" errors for sites that use "/~username" type installations (such as a dev site).
The fix is to do this:
This will fix file not found errors on ~username based installations.
Comment #11
crystaldawn commentedI found another bug that may or may not be related to the patch I included. I didnt remember this part but the webform field key has to match the salesforce field key in order for the dropdown salesforce field map selection to stick. If it doesnt match, the dropdown reverts back to Select a field. I consider this a bug. It should not do this. I am going to look into why its doing this as it defeats the purpose of making things easy. The intended feature of this drop down was so that you wouldnt need to check the salesforce page at all when dealing with the fields in webform.
Another bug I also noticed is that the WebformSID field is not autocreated if it's missing. I had intended to do this as well but it seems that part didnt make it into my zipfile. I'll have to figure out how I had done that part as well.
Comment #12
obsidiandesign commentedI have a copy that is running with your changes and a few others on my laptop, I'll commit it tonight to -dev. Then, we can work on some of these related issues that have come up in your testing.
Bryan
Comment #13
crystaldawn commentedI have determined that the bugs I found regarding the dropdown not saving unless the keys match is because I forgot to document some changes to the salesforcewebform.module file when I first put this together. I dont know if I have time to go through and redo those changes but if I do, I'll post them here. Otherwise all I can do is say that the method for saving the field form data needs to change in order to make the UI more user friendly. Webform field's should not need to be the same as the salesforce fields (this included the webformSID field. I do remember changing how that worked). That was the whole intention of this zip, to make things user friendly and having to keep field names the same is not friendly at all. The client I wrote this for has long been completed and is now off doing their own thing and their source is no longer available on my dev servers. I guess thats a lesson in not deleting completed work lol.
Comment #14
obsidiandesign commentedI'm almost 100% sure that the keys don't have to match the salesforce key. I've used this with several clients with all sorts of webform key names and they don't have to match. I'll check again, but I think you're looking into something you don't have to.
Comment #15
obsidiandesign commentedA slightly modified version of the initial patch has been committed to -dev. Now, we can work on refining it. I will note that it works perfectly on the client installation.
Comment #16
crystaldawn commentedCoolio. I'll try the dev version instead so we can work out patches to that :D TY
Comment #17
amanire commentedIs there a method for pulling picklist options into the webform or do these transactions get really hairy on a field-level basis? That would improve the UI for clients significantly and reduce errors. Maybe I should post this as a separate feature request?
Comment #18
obsidiandesign commented@amanire: try out the development version - it has the custom fields pulled directly from Salesforce. It needs testing, so this would help get it into a release.
Comment #19
bwoods commentedSorry for not commenting again sooner. You were right, the issue was that I didn't have the latest dev release, and I had only two arguments. I just upgraded to the latest dev version, and everything works without my previous workaround.
Comment #20
bwoods commentedWell, I thought everything was working properly, but I was wrong ... I had to again make the change I mentioned in #5.
I did upgrade to the latest dev version.
Comment #21
obsidiandesign commentedAfter success with 3 client installs & local testing, I've committed this to a 6.x-1.3 version release. Thanks crystaldawn for the initial patch & for those who helped test.
Bryan O'Shea
Obsidian Design
Comment #22
crystaldawn commentedOk, so I had mentioned previously that if the field NAME (not the label) in the webform did not match the Salesforce fieldname EXACTLY, then it would simply not save. This can be reproduced by simply creating a new field, naming it something like ertwerwrtyrty and then selecting a salesforce field to map it to and clickin save. Then go back to edit that same field and you'll notice that it does not save the value you set for the salesforce field. Here is why it does that:
On line 95 in salesforcewebform.module it has this line:
'#default_value' =>empty($form['#parameters'][3]['form_key']) ? '' : $form['#parameters'][3]['form_key'],
Now, array element$form['#parameters'][3]['form_key'] array is nothing more than the "Drupal Machine name" or the "webform field name" of the field that you were editing. So, no matter what you change the salesforce fieldname to, it's always going to have a value of whatever your drupal webform fieldname is.
To fix this is very very simple. I hadnt done this in the patch but I do remember doing this AFTER I created the patch but I guess I didnt post it. Here is what I did: I installed Queryable Variables which is a quickie method to get a fancy storage engine. I dont suggest using this as it would add a requirement to this module, but you can if you like, its pretty slick. Instead, I recommend creating a simple table with a few fields in it that will store the WF -> SF field mappings. Maybe something like:
id
nid
fieldname
sf_fieldname
These are the same fields that QV's uses. ID isnt really used for anything but I always create a table that has an ID field anyways for sorting and what not. All QV's have an ID as well.
So, once QV's is installed, add the following code on line 87
Then on line 104 comment out the default_value entry and replace it like this:
Now that we have the mappings stored and working properly on the forms, we need the same mappings set to salesforce as well. To do this we simply hack up the process function a little by re-arranging the array keys and values right before they are sent to salesforce.
On line 273 in the salesforcewebform_process() function right after the $form_values = $form_state['values']; line put the following:
And thats it. Then the salesforce mappings can be mapped to the drupal webform field no matter what the field name is called. I recommend using your own storage method, maybe create a new save_sf_mapping($nid, $fieldname, $sf_fieldname) get_sf_mapping($nid, $fieldname) function or something like that to make it nice and tidy. Or you can use QV's whichever you prefer, they both will work just fine. The code here shows how to use QV's because I already had it installed and it allows me to store things without having a gazzillion extra tables in my db. It's used just like drupal's variable_get/set/del functions except that it doesnt load everything into memory like the variables table and thus doesnt affect system performance when the table gets extremely large and it is far more flexible in general.
Comment #23
obsidiandesign commented@crystaldawn: I can't replicate the problem, even with crazy Webform field names including numbers in either the 1.x or 2.x branch of this module. Is there maybe something else causing the problem for you? Or does anyone else have this issue?
Comment #24
crystaldawn commentedThe issue is completely explained above as to how this is the case. So everyone has this issue. Its not even possible that it could work for you unless you have somehow fixed the bug inadvertantly with your implementation. If you look on line 95 in salesforcewebform.module, you'll see that the default value is filled in with the wrong value. Its filled in with the WEBFORM field name rather than the selected field value. It will only work if BOTH values are identical. My guess is that your webform field AND salesforce field names are identical which would cause you to NOT see the problem.
I also found a slight bug regarding Case and field names. Salesforce seems to send the fieldnames in different cases which causes PHP to have TWO versions of the same field in the salesforce object. To fix this, simply lowercase ALL the fields in the object and then you will end up with the correct object that needs to be sent to salesforce. The below code does this. Simply search for $success = in the module and put the following code directly above it.