We’ve implemented a custom JavaScript ranking algorithm for supplier evaluation in our sourcing module. The script works perfectly when processing individual suppliers through the UI, but consistently fails during bulk CSV imports with 50+ records.
The error occurs in our bulk import process:
var score = supplier.getProperty('quality_rating') * 0.4;
score += supplier.getProperty('delivery_performance') * 0.3;
// Error: Cannot read property 'quality_rating' of undefined
Our custom JavaScript ranking logic calculates weighted scores based on quality ratings, delivery performance, and cost factors. The script throws ‘undefined property’ errors specifically during bulk operations, suggesting the supplier object isn’t fully initialized when our ranking method executes. Individual imports work because there’s sufficient time for property population.
This is blocking our quarterly supplier onboarding process where we typically import 80-100 new vendors. We’ve tried adding delays and checking for null values, but the timing issue persists. Has anyone encountered similar null/undefined property errors in custom bulk import scenarios?
I’ve seen this pattern before with custom scripts in bulk operations. The issue is that bulk imports bypass some of the standard lifecycle events that populate related properties. Your ranking script is likely executing before the supplier item’s properties are committed to the database. Try wrapping your property access in a null check and queuing the ranking calculation as a post-import event instead of inline.
Thanks for the suggestions. I tried adding explicit null checks, but the properties are literally undefined in the bulk context, not just null. The supplier object exists but getProperty() returns undefined for our custom fields. Could this be related to how the bulk import processes relationships versus direct field values? Our quality_rating field is calculated from multiple source relationships.
That’s your problem right there. Calculated fields and relationship-based properties aren’t available during the initial bulk import transaction. The import process creates the base items first, then processes relationships in a second pass. Your ranking script needs to wait for the relationship resolution phase. You should move your custom JavaScript ranking to an onAfterAdd server event with a conditional check that verifies all required relationships exist before calculating the score. For bulk imports specifically, consider implementing a batch job that runs post-import to recalculate all supplier rankings once relationships are fully established.
I’m dealing with this exact scenario in our sourcing implementation. The issue is definitely the relationship timing during bulk operations. For our supplier scoring, we ended up using a hybrid approach where simple fields are calculated inline, but complex relationship-dependent scores are deferred to a background process.
We had similar undefined errors with our custom vendor scoring. The problem was that during bulk import, the item context doesn’t include all the relationships and calculated fields that are available in the UI. We ended up creating a separate server method that runs after the import completes, which retrieves the full supplier item with all properties populated. This two-phase approach solved our timing issues completely.
Another option is to modify your bulk import template to include the ranking calculation as a post-processing step. We use a similar approach where the CSV import creates the basic supplier records, then a scheduled workflow processes the batch to calculate derived values. This separates the import from the calculation and ensures all dependencies are resolved.
The root cause is that your bulk import process is executing the custom JavaScript ranking before relationship resolution completes. Here’s a comprehensive solution addressing all three focus areas:
Bulk Import Process Fix:
Modify your import workflow to use a two-phase approach. Phase one imports the base supplier data without triggering the ranking script. Phase two runs after all relationships are committed.
Custom JavaScript Ranking Refactor:
Update your ranking script with defensive property access:
var qualityRating = supplier.getProperty('quality_rating');
var deliveryPerf = supplier.getProperty('delivery_performance');
if (!qualityRating || !deliveryPerf) {
return null; // Skip ranking, will be calculated later
}
Null/Undefined Property Error Resolution:
Implement a server event that triggers onAfterAdd for supplier items. Add a conditional check that verifies all required relationship properties exist before executing ranking logic:
// In onAfterAdd server event
var item = this.getInnovator().getItemById('Supplier', supplierId);
if (item.getProperty('quality_rating') &&
item.getProperty('delivery_performance')) {
// All dependencies resolved, calculate ranking
calculateSupplierRanking(item);
} else {
// Queue for batch processing
addToPendingRankingQueue(supplierId);
}
For the bulk import scenario specifically, create a scheduled server method that runs 5 minutes after import completion:
// Batch ranking processor
var pendingSuppliers = inn.applyAML(
"<AML><Item type='Supplier' action='get'>" +
"<ranking_score is_null='1'/>" +
"<created_on condition='gt'>" + lastImportTime + "</created_on>" +
"</Item></AML>"
);
This approach ensures your custom ranking logic has access to fully populated supplier objects with all relationship data available. The two-phase process separates data import from calculation, eliminating the undefined property errors while maintaining data integrity.
For immediate relief, disable the inline ranking calculation in your import configuration and run a one-time batch update to calculate rankings for all recently imported suppliers. Going forward, this architecture will handle both individual UI-based supplier creation and bulk CSV imports reliably.