NetSuite Bin Transfer Custom Fields
Sometimes it becomes necessary to customize the NetSuite Bin Transfer, unfortunately as of 2018.2 this ability is still not supported. I looked around and couldn't find an existing workaround published so I decided to share mine. Perhaps you want to change the page layout or just add some custom fields, in either case here is the simple yet effective workaround I have used for both.
You will need to create the following
- Custom Record - For storing your custom fields
- Custom fields - Fields you want to see on your bin transfer, add them to your custom record.
- A User Event Suite Script - For managing your bin transfer UI and the custom record.
Step 1: Lay the ground work with a Custom Record
While I assume you are familiar with custom records and fields I'll run through it quickly.
- In the UI Navigate to Customization -> Lists, Records, & Fields -> Record Types -> New
- Fill in the "NAME" (i.e. Bin Transfer Fields) and "ID" (i.e. _yourco_bin_transfer_fields) Fields.
- Uncheck "INCLUDE NAME FIELD"
- Select your desired "ACCESS TYPE"
- Select / deselect the remaining options as necessary / desired.
- Save
Step 2: Custom Fields
To link your custom record to your bin transfer the following custom field is required:
- Click "NEW FIELD"
- Fill out the "LABEL" (i.e. Related Bin Transfer) and give it an "ID" (i.e. _yourco_rel_bin_trnsfr)
- Select "TYPE" as List/Record
- Select "LIST/RECORD" as Transaction
- Select Sourcing & Filtering Subtab
- Add a new Filter: "FILTER USING" = Type, "COMPARE TYPE" = equal, "VALUE IS" = bin transfer
- Add, then Save
The remaining custom fields can be added as needed / desired to your custom record the same way using whatever types your project requires.
Step 3: Using SuiteScript to pull it all together
I'm also assuming you are familiar with NetSuite SuiteScripts, creating them, and deploying them. You will need to create a new USER EVENT script and deploy it to your bin transfer records. Your SuiteScript will require the following modules:
/**
* @NApiVersion 2.x
* @NScriptType UserEventScript
* @NModuleScope SameAccount
*/
define(['N/record', 'N/search','N/log', 'N/ui/serverWidget'],
/**
* @param {record} record
* @param {search} search
* @param {log} log
* @param {serverWidget} serverWidget
*/
function(record, search, log, serverWidget) {
You will need to use all 3 methods, Before Load, Before Submit, and After Submit.
Before Load serves 3 functions, it is where you can modify your UI layout like:
You can add form groups like:
var form = scriptContext.form;
//Add Form Groups to Bin Transfer
form.addFieldGroup({
id : 'custpage_yourco_bt_priFG',
label : 'Primary Information'
});
form.addFieldGroup({
id : 'custpage_yourco_bt_related_FG',
label : 'Related Information'
});
You can move existing fields into the new field groups like this, I added a marker field to start my placement with:
var marker = form.addField({
id : 'custpage_yourco_bt_marker',
type : serverWidget.FieldType.INLINEHTML,
label : 'Marker',
container : 'custpage_yourco_bt_priFG'
});
marker.defaultValue = "<script></script>"
Grab your pre-existing fields like:
var transactionnumber = form.getField({
id : 'transactionnumber'
});
var tranid = form.getField({
id : 'tranid'
});
var trandate = form.getField({
id : 'trandate'
});
var location = form.getField({
id : 'location'
});
var subsidiary = form.getField({
id : 'subsidiary'
});
var generatetranidonsave = form.getField({
id : 'generatetranidonsave'
});
var memo = form.getField({
id : 'memo'
});
Then insert your fields into the new form group:
form.insertField({
field : memo,
nextfield : 'custpage_yourco_bt_marker'
});
form.insertField({
field : trandate,
nextfield : 'memo'
});
form.insertField({
field : subsidiary,
nextfield : 'trandate'
});
form.insertField({
field : location,
nextfield : 'subsidiary'
});
if(scriptContext.type == 'create'){
form.insertField({
field : generatetranidonsave,
nextfield : 'location'
});
form.insertField({
field : transactionnumber,
nextfield : 'generatetranidonsave'
});
} else {
form.insertField({
field : transactionnumber,
nextfield : 'location'
});
}
form.insertField({
field : tranid,
nextfield : 'transactionnumber'
});
Keep in mind you are inserting fields from the marker backwards, right to left, bottom to top. When your done your bin transfer should now look a little cleaner, like:
To add your custom fields simply create and stick them into your new field group:
var moveType = form.addField({
id : 'custpage_yourco_bt_type',
type : serverWidget.FieldType.SELECT,
source : 'customlist_yourco_bt_types',
label : 'Move Type',
container : 'custpage_yourco_bt_related_FG'
});
moveType.setHelpText({
help : "Select the move type, Bin Move is the default."
});
moveType.defaultValue = 1;
This particular field is used to show what type of bin transfer we are doing, this is for a particular business use case but shows a good example. Don't forget to set the help text for your fields, its a courtesy for the end user!
Now you have a cleaned up UI AND a custom field on your ui like:
Now you load & link existing related field data from your custom record:
if(scriptContext.type == 'edit' || scriptContext.type == 'view'){
var cRecord = scriptContext.newRecord;
var bm = getAdditionalFields(cRecord.getValue({fieldId: 'id'}));
if(bm.internalid > 0){
moveType.defaultValue = bm.type;
}
}
The getAdditionalFields is a simple shared method to use across the 3 primary User Event methods:
function getAdditionalFields(bmId){
var bm = {
internalid: -1,
type: 1,
binMove: -1,
}
if(bmId > 0){
search.create({
type: 'customrecord_yourco_bin_transfer_fields',
columns: [{
name: 'internalid'
},{
name: 'custrecord_yourco_rel_bin_trnsfr'
},{
name: 'custrecord_yourco_bin_move_type'
}],
filters: ["custrecord_yourco_bt","anyof", bmId]
}).run().each(function(result) {
bm.internalid = result.getValue({name: 'internalid'});
bm.binMove = result.getValue({name: 'custrecord_yourco_rel_bin_trnsfr'});
bm.type = result.getValue({name: 'custrecord_yourco_bin_move_type'});
});
}
return bm;
}
}
Before Submit handles your data for the Edit, View, & Delete contexts.
function beforeSubmit(scriptContext) {
//Save Existing Bin Transfer related fields if changed
try{
var cRecord = scriptContext.newRecord;
var toSave = false;
var bm = getAdditionalFields(scriptContext.newRecord.id);
//Were are deleting the Bin Transfer, delete related record
if(scriptContext.type == 'delete'){
var bm = getAdditionalFields(scriptContext.oldRecord.id);
if(bm.internalid > 0){
record.delete({
type: 'customrecord_yourco_bin_transfer_fields',
id: bm.internalid,
});
}
}
//Check for and Save changes from Bin Transfer
if((scriptContext.type == 'edit' || scriptContext.type == 'view') && bm.internalid > 0){
var bmFields = record.load({
type: 'customrecord_yourco_bin_transfer_fields',
id: bm.internalid,
isDynamic: true,
});
var newType = cRecord.getValue({fieldId: 'custpage_yourco_bm_type'});
if(newType != bm.type){
toSave = true;
bmFields.setValue({
fieldId: 'custrecord_yourco_bin_move_type',
value: newType
});
}
if(toSave == true){
bmFields.save();
}
}
}catch(e){
log.error({
title: 'Bin Transfer Related Fields Save Error',
details: e.message
});
}
}
After Submit handles your create context:
function afterSubmit(scriptContext) {
//Create New Bin Transfer related fields
try{
if(scriptContext.type == 'create'){
var cRecord = scriptContext.newRecord;
var bmFields = record.create({
type: 'customrecord_yourco_bin_transfer_fields',
isDynamic: false
});
bmFields.setValue({
fieldId: 'custrecord_yourco_rel_bin_trnsfr',
value: scriptContext.newRecord.id
});
bmFields.setValue({
fieldId: 'custrecord_yourco_bin_move_type',
value: cRecord.getValue({fieldId: 'custpage_yourco_bm_type'})
});
bmFields.save();
}
}catch(e){
log.error({
title: 'Bin Transfer Related Fields Save Error',
details: e.message
});
}
}
Finally, to conclude
While this post seems longer than I intended when I began, the concepts should be familiar. This is a great way to use existing components to solve a small limitation. Feel free to reach out to me any time with questions, feedback, or suggestions.
Hi Andre, your instruction are very usefull. Thank you so much!! I used them. Do you know how to do for adding some line field to Bin Transfer? Thank you in advance