I've updated our test environment to the latest version of Acumatica 5.10.0752. After updating our sync process has started to fail when inserting an item into a sales order. Note that no code changes were implemented to the sync process and the only change was to apply the latest update to Acumatica. I've been struggling with this and can't seem to solve adequately and could use a bit of help..
Here is the stack trace:
System.Web.Services.Protocols.SoapException: Server was unable to process request. ---> PX.Data.PXException: Error #112: An error occurred while processing the field InventoryID : Object reference not set to an instance of an object.. ---> System.NullReferenceException: Object reference not set to an instance of an object. at PX.Objects.SO.SOOrderEntry.SOLine_CuryUnitCost_FieldDefaulting(PXCache sender, PXFieldDefaultingEventArgs e) at PX.Data.PXCache.OnFieldDefaulting(String name, Object row, Object& newValue) at PX.Data.PXCache1.SetDefaultExt(Object data, String fieldName) at PX.Objects.SO.SOOrderEntry.SOLine_UOM_FieldUpdated(PXCache sender, PXFieldUpdatedEventArgs e) at PX.Data.PXFieldUpdated.Invoke(PXCache sender, PXFieldUpdatedEventArgs args) at PX.Data.PXCache.OnFieldUpdated(String name, Object row, Object oldValue, Boolean externalCall) at PX.Data.PXCache1.SetDefaultExt(Object data, String fieldName) at PX.Objects.SO.SOOrderEntry.SOLine_InventoryID_FieldUpdated(PXCache sender, PXFieldUpdatedEventArgs e) at PX.Data.PXFieldUpdated.Invoke(PXCache sender, PXFieldUpdatedEventArgs args) at PX.Data.PXCache.OnFieldUpdated(String name, Object row, Object oldValue, Boolean externalCall) at PX.Data.PXCache1.a(TNode A_0, TNode A_1, IDictionary A_2, PXCacheOperation A_3, Boolean A_4) --- End of inner exception stack trace --- at PX.Data.PXCache1.a(TNode A_0, TNode A_1, IDictionary A_2, PXCacheOperation A_3, Boolean A_4) at PX.Data.PXCache1.a(TNode A_0, TNode A_1, IDictionary A_2, PXCacheOperation A_3) at PX.Data.PXCache1.Insert(IDictionary values) at PX.Data.PXCache1.Update(IDictionary keys, IDictionary values) at PX.Data.PXGraph.ExecuteUpdate(String viewName, IDictionary keys, IDictionary values, Object[] parameters) at PX.Data.PXGraph.CopyPasteCommitChanges(String viewName, OrderedDictionary keys, OrderedDictionary vals) at PX.Api.SyImportProcessor.SyStep.CommitChanges(Object itemToBypass, PXFilterRow[] targetConditions) at PX.Api.SyImportProcessor.ExportTableHelper.ExportTable() at PX.Api.ScreenUtils.Submit(String screenId, Command[] commands, SchemaMode schemaMode, PXGraph& graph, String& redirectContainerView, String& redirectScreen, Boolean mobile) at PX.Api.Services.ScreenService.Submit(String id, IEnumerable1 commands, SchemaMode schemaMode, Boolean mobile, PXGraph& forceGraph, String& redirectContainerView, String& redirectScreen) at PX.Api.Services.ScreenService.Submit(String id, IEnumerable`1 commands, SchemaMode schemaMode) at PX.Api.Soap.Screen.ScreenGate.Submit(Command[] commands) --- End of inner exception stack trace ---
Here is a code snippet that worked fine before the update:
cmds.Add( SO301000.DocumentDetails.ServiceCommands.NewRow );
cmds.Add( new AcumaticaApiWS.Value { Value = item.InventoryId, LinkedCommand = SO301000.DocumentDetails.InventoryID } );
cmds.Add( new AcumaticaApiWS.Value { Value = item.Quantity, LinkedCommand = SO301000.DocumentDetails.Quantity } );
cmds.Add( new AcumaticaApiWS.Value { Value = item.UnitPrice, LinkedCommand = SO301000.DocumentDetails.UnitPrice } );
cmds.Add( new AcumaticaApiWS.Value { Value = item.WebCode, LinkedCommand = SO301000.DocumentDetails.WebCode } );
cmds.Add( new AcumaticaApiWS.Value { Value = item.ExtPrice, LinkedCommand = SO301000.DocumentDetails.ExtPrice} );
cmds.Add( new AcumaticaApiWS.Value { Value = item.ReasonCode, LinkedCommand = SO301000.DocumentDetails.ReasonCode } );
cmds.Add( new AcumaticaApiWS.Value { Value = item.LineDescription, LinkedCommand = SO301000.DocumentDetails.LineDescription } );
cmds.Add( SO301000.Actions.Save );
try
{
this.context.SO301000Submit( cmds.ToArray() );
}
catch( Exception ex )
{
...
}
It seems to be related to UOM but I'm not sure what the issue is. Thinking that there might be a some configuration somewhere that needs to be setup. But not seeing what it could be.
If I add this line of code right after the new row command, it works fine.
cmds.Add( new AcumaticaApiWS.Value { Value = "EA", LinkedCommand = SO301000.DocumentDetails.UOM } );
However, I would prefer it to get the UOM from the item's inventory default as it was before the update.
Any help would be greatly appreciated.
** Another thought we had was that when we skipped updates by installing just the latest version without installing each of the versions in between we inadvertently caused this issue. - Could that cause weird behavior - skipping updates to just install the latest? Tx
Regarding stack trace you need to set UOM
Related
I'm trying to process return orders in Acumatica, for which I will have to create a Sales Order of type RC, invoke the Create Receipt Action on the sales order which creates a shipment of type Receipt and then invoke Confirm Shipment on the shipment. However in the list of Actions defined on the Sales Order, I do not find an action corresponding to Create Receipt. Can anyone guide me on how to invoke the Create Receipt action programatically as we do through the screen?
For e.g. this is how I invoke Confirm Shipment on a shipment and looking for something similar to Create Receipt:
var adapter = new PXAdapter(graph.CurrentDocument);
adapter.Arguments.Add("actionID", SOShipmentEntryActionsAttribute.ConfirmShipment);
PXLongOperation.StartOperation(graph, delegate ()
{
foreach (SOShipment soShipment in graph.action.Press(adapter)) ;
});
This is a solution previously provided by Acumatica, I tried this method in few screens and it was working. In the following code try to change the graph to your SOOrderEntry and Command to "Create Receipt"
docgraph.Document.Current = docgraph.Document.Search<SOShipment.shipmentNbr>("mYsHIPMENTnUMBER");
docgraph.Cancel.Press();
foreach (var action in (docgraph.action.GetState(null) as PXButtonState).Menus)
{
if (action.Command == "Confirm Shipment")
{
PXAdapter adapter2 = new PXAdapter(new DummyView(docgraph, docgraph.Document.View.BqlSelect, new List<object> { docgraph.Document.Current }));
adapter2.Menu = action.Command;
docgraph.action.PressButton(adapter2);
}
}
internal class DummyView : PXView
{
List<object> _Records;
internal DummyView(PXGraph graph, BqlCommand command, List<object> records)
: base(graph, true, command)
{
_Records = records;
}
public override List<object> Select(object[] currents, object[] parameters, object[] searches, string[] sortcolumns, bool[] descendings, PXFilterRow[] filters, ref int startRow, int maximumRows, ref int totalRows)
{
return _Records;
}
}
I am trying to insert a new record into a custom table in the database. This is being performed through a graph extension onto the SO graph. The code is as follows:
public PXAction<PX.Objects.SO.SOOrder> addToDatabase;
[PXButton(CommitChanges = true)]
[PXUIField(DisplayName = "Send to Manufacturing")]
protected void AddToDatabase()
{
try
{
Flow2 graphWO = PXGraph.CreateInstance<Flow2>();
EMPWorkOrder wo = null;
foreach (PXResult<SOLine, InventoryItem> line in PXSelectJoin<SOLine, LeftJoinSingleTable<InventoryItem, On<InventoryItem.inventoryID, Equal<SOLine.inventoryID>>>,
Where<SOLine.orderNbr, Equal<Current<SOOrder.orderNbr>>>>.Select(Base, Base.Document.Current.OrderNbr))
{
PXCache sender = Base.Transactions.Cache;
SOLine soLine = (SOLine)line;
InventoryItem item = (InventoryItem)line;
SOLineExt lineExt = sender.GetExtension<SOLineExt>(soLine);
if (lineExt.UsrisSentToManufacturing != true)
{
wo = new EMPWorkOrder();
wo.Soid = Base.Document.Current.OrderNbr;
wo.ItemCD = item.InventoryCD;
wo.LineNbr = soLine.LineNbr;
wo.QtyReceived = 0;
wo.DateReceived = null;
wo.QtyComplete = 0;
wo.QtySentToInventory = 0;
wo.RouteId = "0";
wo.KitId = -1;
wo.IsStarted = false;
wo.NoteID = Guid.NewGuid();
graphWO.Document.Insert(wo);
graphWO.Actions.PressSave();
graphWO.Clear();
}
}
throw new PXException("Successfully moved to Manufacturing");
}
}
When executing the code, the error I receive is the following:
Error#14: Inserting 'EMPWorkOrder' record raised one or more errors. Please review.
When I go into the trace, this is the information it gives me:
12/16/2016 1:44:23 PM Error:
Error #14: Inserting 'EMPWorkOrder' record raised one or more errors. Please review.
at PX.Objects.SO.SOOrderEntry_Extension.AddToDatabase()
at PX.Data.PXAction`1.<>c__DisplayClass3_0.<.ctor>b__0(PXAdapter adapter)
at PX.Data.PXAction`1.a(PXAdapter A_0)
at PX.Data.PXAction`1.d__31.MoveNext()
at PX.Data.PXAction`1.d__31.MoveNext()
at PX.Web.UI.PXBaseDataSource.tryExecutePendingCommand(String viewName, >String[] sortcolumns, Boolean[] descendings, Object[] searches, Object[] >parameters, PXFilterRow[] filters, DataSourceSelectArguments arguments, >Boolean& closeWindowRequired, Int32& adapterStartRow, Int32& adapterTotalRows)
at PX.Web.UI.PXBaseDataSource.ExecuteSelect(String viewName, DataSourceSelectArguments arguments, PXDSSelectArguments pxarguments)
Is there any reason that my record wouldn't be inserting into the custom table I made? If you need any other information to develop a resolution to this issue, please feel free to ask.
Eric, you most likely get this error because of some empty field or fields (with no value or null value assigned) decorated with the PXDefaultAttribute. While running the code under debugger, you should get access to a more detailed exception through the InnerException property of the originally thrown exception.
On a side note, let me also advise you to add SOLine.orderType field in Where clause of your BQL query in the beginning of action delegate, as there are 2 key fields defined for the SOOrder DAC has: OrderType and OrderNbr
I attempting to add a folder to a custom Document Set with in a Document library. However something is not right one or more of the fields and the following error message is not providing me info that would narrow it down. I am looking for a way to identify and fix the offending fields in library.
Microsoft.SharePoint.Client.ServerException was unhandled
HResult=-2146233088
Message=One or more field types are not installed properly. Go to the list settings page to delete these fields.
ServerErrorCode=-2130575340
ServerErrorTraceCorrelationId=0e7a749d-70a8-2000-36cf-14f8618874a2
ServerErrorTypeName=Microsoft.SharePoint.SPException
ServerStackTrace=""
Source=Microsoft.SharePoint.Client.Runtime
StackTrace:
at Microsoft.SharePoint.Client.ClientRequest.ProcessResponseStream(Stream responseStream)
at Microsoft.SharePoint.Client.ClientRequest.ProcessResponse()
at Microsoft.SharePoint.Client.ClientRequest.ExecuteQueryToServer(ChunkStringBuilder sb)
at Microsoft.SharePoint.Client.ClientRequest.ExecuteQuery()
at Microsoft.SharePoint.Client.ClientRuntimeContext.ExecuteQuery()
at Microsoft.SharePoint.Client.ClientContext.ExecuteQuery()
at Microsoft.SharePoint.Client.ClientContextExtensions.ExecuteQueryImplementation(ClientRuntimeContext clientContext, Int32 retryCount, Int32 delay)
at Microsoft.SharePoint.Client.FileFolderExtensions.CreateFolderImplementation(FolderCollection folderCollection, String folderName, Folder parentFolder)
at Microsoft.SharePoint.Client.FileFolderExtensions.CreateFolder(Folder parentFolder, String folderName)
at AddFolderToDocSet.Program.Main(String[] args) in C:\Users\user\Documents\Visual Studio 2015\Projects\PnPCoreTest\AddFolderToDocSet\Program.cs:line 51
at System.AppDomain._nExecuteAssembly(RuntimeAssembly assembly, String[] args)
at System.AppDomain.ExecuteAssembly(String assemblyFile, Evidence assemblySecurity, String[] args)
at Microsoft.VisualStudio.HostingProcess.HostProc.RunUsersAssembly()
at System.Threading.ThreadHelper.ThreadStart_Context(Object state)
at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preserveSyncCtx)
at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preserveSyncCtx)
at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)
at System.Threading.ThreadHelper.ThreadStart()
InnerException:
This is the code I am using to add the folder which leverages the PNP-Sites-Core library.
// Get Root Folders collection for
var projLibRootFldrs = prjLib.RootFolder;
ctx.Load(projLibRootFldrs, pf => pf.Folders);
ctx.ExecuteQueryRetry();
// Get the Document Set
Folder f = projLibRootFldrs.EnsureFolder("Test1");
f.CreateFolder("foo"); // Error here
Update: 4/21/2016
After painstaking analysis (errr... trial, error, repeat for ever) I have narrowed this down to the fields in the "Shared Columns" section of the "Document Set Settings" It seems when I check any of those the error occurs. When I uncheck all the fields so none are shared I am able to add the folder.
Update: 4/26/2016
Here are the exact steps needed to recreate this error.
Here is the exact console program used to create the folder:
static void Main(string[] args)
{
string pwd = System.Environment.GetEnvironmentVariable("SOME_PWD", EnvironmentVariableTarget.User);
if (string.IsNullOrEmpty(pwd))
{
System.Console.Write("MSOPWD user environment variable empty, cannot continue. Press any key to end.");
System.Console.ReadKey();
return;
}
// Get access to source site
using (var ctx = new ClientContext("https://mysite.sharepoint.com/sites/demo3"))
{
//Provide count and pwd for connecting to the source
var passWord = new SecureString();
foreach (char c in pwd.ToCharArray()) passWord.AppendChar(c);
ctx.Credentials = new SharePointOnlineCredentials("me#email.com", passWord);
Web web = ctx.Web;
string docSetLibName = "P1";
string docSetFolderName = "Test1";
string folderName = "Foo1";
try
{
List list = EnsureTargetTestFolder(ctx, docSetLibName);
Folder docSet = EnsureTestDocumentSet(ctx, list, docSetFolderName);
MakeStandardFolder(ctx, docSet, folderName);
}catch(Exception exp)
{
Console.ForegroundColor = ConsoleColor.White;
Console.BackgroundColor = ConsoleColor.Black;
Console.WriteLine("ERROR:" + Environment.NewLine);
Console.WriteLine(exp.Message + Environment.NewLine);
Console.WriteLine(Environment.NewLine);
Console.ResetColor();
}
Console.WriteLine("Done...");
}
Console.ReadKey();
}
private static List EnsureTargetTestFolder(ClientContext ctx, string docSetLibName)
{
if (ctx.Web.ListExists(docSetLibName) == false) {
Console.WriteLine(String.Format("List {0} not found... creating new!", docSetLibName));
// Make the list
List newList = ctx.Web.CreateList(ListTemplateType.DocumentLibrary, docSetLibName, false, true, "", true);
newList.AddContentTypeToListByName("DocSetTest");
newList.RemoveContentTypeByName("Document");
newList.EnableFolderCreation = true;
return newList;
}else
{
Console.WriteLine(String.Format("List {0} exists!", docSetLibName));
return ctx.Web.GetListByTitle(docSetLibName);
}
}
private static Folder EnsureTestDocumentSet(ClientContext ctx, List list, string docSetLibName)
{
if (list.RootFolder.FolderExists(docSetLibName) == false)
{
Console.WriteLine(String.Format("Document Set '{0}'does not exist... creating new!", docSetLibName));
Folder fldr = list.RootFolder.CreateDocumentSet(docSetLibName, ctx.Web.GetContentTypeByName("DocSetTest").Id);
return fldr;
}else
{
Console.WriteLine(String.Format("Document Set '{0}\\{1}' exists", list.EntityTypeName, docSetLibName));
return list.RootFolder.ResolveSubFolder(docSetLibName);
}
}
private static void MakeStandardFolder(ClientContext ctx, Folder docSet, string folderName)
{
if (docSet.FolderExists(folderName) == false)
{
Console.WriteLine(String.Format("Folder {0} does not exist ... creating new!", folderName));
docSet.CreateFolder(folderName);
}else
{
Console.WriteLine(String.Format("Folder {0} already exists", folderName));
}
}
I have tested the steps you provided . Yes , with your steps the error occured .
I notice the "DocSetTest ID" column may cause the error :
1.create "DocumentSetName ID" column and make it shared , the error occured .
2.create "ID" column and make it shared , the error occured .
3.create "DocumentSetName_ID" column and make it shared , it works fine .
4.create "IDDocumentSetName" column and make it shared , it works fine .
So maybe your "ID" or "DocumentSetName ID" column may conflict something (perhaps existed "ID" column) when using OfficeDevPnP.Core library. Try to change the name of the columns and check the results .
The trick to making this work was to first access and remove the fields in the SharedFields collection of the DocumentSetTemplate, then make the folder, then restore the SharedFields. Here are the methods used to do this.
private static void HideSharedFields(ClientContext ctx, ContentType ct, out SharedFieldCollection unsharedFields)
{
DocumentSetTemplate docSetTemplate = DocumentSetTemplate.GetDocumentSetTemplate(ctx, ct);
SharedFieldCollection sharedFields = docSetTemplate.SharedFields;
unsharedFields = sharedFields;
ctx.Load(sharedFields);
ctx.ExecuteQueryRetry();
foreach(var fld in sharedFields)
{
Console.WriteLine(String.Format(" - Removing SharedField '{0}'", fld.Title));
docSetTemplate.SharedFields.Remove(fld);
fld.UpdateAndPushChanges(true);
}
docSetTemplate.Update(true);
ctx.ExecuteQueryRetry();
}
private static void RevealSharedFields(ClientContext ctx, ContentType ct, SharedFieldCollection unsharedFields)
{
DocumentSetTemplate docSetTemplate = DocumentSetTemplate.GetDocumentSetTemplate(ctx, ct);
foreach (var fld in unsharedFields)
{
Console.WriteLine(String.Format(" + Adding SharedField '{0}'", fld.Title));
docSetTemplate.SharedFields.Add(fld);
fld.UpdateAndPushChanges(true);
}
docSetTemplate.Update(true);
ctx.ExecuteQueryRetry();
}
I'm trying to use the Acumatica API to convert a Business Account to a Customer on Acumatica 5.20.2067. The code I'm using is based on converting a Lead to a Business Account. Converting a Business Account to a Customer seems simpler than converting a Lead because converting a Business Account does not pop up a dialog box. However, I've tried it two ways and one produces an error and the other creates a completely separate Customer record instead of converting the existing Business Account.
Based on the code in the other post about converting a Lead, here is the code that I think should work:
Public Function ConvertBusinessAccountToCustomer(ByVal baID As String, ByVal firstName As String, ByVal LastName As String)
Dim CR303000 As CR303000Content = m_context.CR303000GetSchema()
m_context.CR303000Clear()
Dim AR303000 As AR303000Content = m_context.AR303000GetSchema()
m_context.AR303000Clear()
' call the Action to convert the BA to a Customer
Dim baKeyVal As Value = CreateValue(CR303000.AccountSummary.BusinessAccount, baID)
Dim updateBACommands As Command() = {baKeyVal, CR303000.Actions.ConverToCustomer}
Dim updateBaResult As CR303000Content() = m_context.CR303000Submit(updateBACommands)
' just like with Lead, the Customer record now needs to be saved
' add other fields required for Customer
Dim customerNameVal As Value = CreateValue(AR303000.CustomerSummary.CustomerName, CreateCustomerFullName(firstName, LastName))
Dim classVal As Value = CreateValue(AR303000.GeneralInfoFinancialSettings.CustomerClass, "DEFAULT")
Dim statementCycleVal As Value = CreateValue(AR303000.GeneralInfoFinancialSettings.StatementCycleID, "ENDOFMONTH")
Dim statementTypeVal As Value = CreateValue(AR303000.BillingSettingsPrintAndEmailSettings.StatementType, "Open Item")
Dim cashDiscountAccountVal As Value = CreateValue(AR303000.GLAccountsCashDiscountAccount.CashDiscountAccount, "10103")
Dim creditVerificationVal As Value = CreateValue(AR303000.GeneralInfoCreditVerificationRulesCreditVerification.CreditVerification, "Disabled")
Dim commandsCustomer As Command() =
{
customerNameVal, classVal, statementCycleVal, statementTypeVal, cashDiscountAccountVal, creditVerificationVal,
AR303000.Actions.Save,
AR303000.CustomerSummary.CustomerID
}
Dim newCustomerContent As AR303000Content() = m_context.AR303000Submit(commandsCustomer)
Dim newCustomerID As String = ""
If newCustomerContent.Length > 0 Then
' this should be exact same as the newBAID, this is just for debugging
newCustomerID = newCustomerContent(0).CustomerSummary.CustomerID.Value
End If
Return newCustomerID
End Function
The result though is that when CR303000Submit is called with the ConverToCustomer action, I get the following error referring to the Default Location Value:
[SoapException: System.Web.Services.Protocols.SoapException: Server was unable to process request.
---> PX.Data.PXFieldValueProcessingException: Error: An error occurred while processing the field Default Location value 15497 Error: Default Location '15497' cannot be found in the system.. ---> PX.Data.PXSetPropertyException: Error: DefLocationID '15497' cannot be found in the system.
at PX.Data.PXSelectorAttribute.throwNoItem(String[] restricted, Boolean external, Object value)
at PX.Data.PXSelectorAttribute.FieldVerifying(PXCache sender, PXFieldVerifyingEventArgs e)
at PX.Data.PXCache.OnFieldVerifying(String name, Object row, Object& newValue, Boolean externalCall)
at PX.Data.PXCache`1.a(TNode& A_0)
--- End of inner exception stack trace ---
at PX.Data.PXCache`1.Insert(Object data, Boolean bypassinterceptor)
at PX.Data.PXCache`1.Insert(Object data, Boolean bypassinterceptor)
at PX.Data.PXCache`1.Insert(Object data)
at PX.Data.PXCache`1.Extend[Parent](Parent item)
at PX.Objects.CR.BusinessAccountMaint.ConverToCustomer(PXAdapter adapter)
at PX.Data.PXAction`1.a(PXAdapter A_0)
at PX.Data.PXAction`1.<Press>d__c.MoveNext()
at PX.Data.PXAction`1.<Press>d__c.MoveNext()
at PX.Api.SyImportProcessor.SyStep.CommitChanges(Object itemToBypass, PXFilterRow[] targetConditions, PXFilterRow[] filtersForAction)
at PX.Api.SyImportProcessor.ExportTableHelper.ExportTable()
at PX.Api.ScreenUtils.Submit(String screenId, Command[] commands, SchemaMode schemaMode, PXGraph& graph, String& redirectContainerView, String& redirectScreen, Boolean mobile, Dictionary`2 viewFilters)
at PX.Api.Services.ScreenService.Submit(String id, IEnumerable`1 commands, SchemaMode schemaMode, Boolean mobile, PXGraph& forceGraph, String& redirectContainerView, String& redirectScreen, Dictionary`2 viewFilters)
at PX.Api.Services.ScreenService.Submit(String id, IEnumerable`1 commands, SchemaMode schemaMode)
at PX.Api.Soap.Screen.ScreenGate.Submit(Command[] commands)
--- End of inner exception stack trace ---]
System.Web.UI.WebControls.Button.System.Web.UI.IPostBackEventHandler.RaisePostBackEvent(String eventArgument) +10
System.Web.UI.Page.RaisePostBackEvent(IPostBackEventHandler sourceControl, String eventArgument) +13
System.Web.UI.Page.RaisePostBackEvent(NameValueCollection postData) +35
System.Web.UI.Page.ProcessRequestMain(Boolean includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint) +1724
Source Error
Line 1555: <System.Web.Services.Protocols.SoapDocumentMethodAttribute("http://www.acumatica.com/generic/CR303000/Submit", RequestNamespace:="http://www.acumatica.com/generic/", ResponseNamespace:="http://www.acumatica.com/generic/", Use:=System.Web.Services.Description.SoapBindingUse.Literal, ParameterStyle:=System.Web.Services.Protocols.SoapParameterStyle.Wrapped)> _
Line 1556: Public Function CR303000Submit(ByVal commands() As Command) As <System.Xml.Serialization.XmlArrayAttribute("SubmitResult"), System.Xml.Serialization.XmlArrayItemAttribute("Content")> CR303000Content()
Line 1557: Dim results() As Object = Me.Invoke("CR303000Submit", New Object() {commands})
Line 1558: Return CType(results(0),CR303000Content())
Line 1559: End Function
The other thing I tried was to change the commands for the CR303000Submit to add a Save action:
Dim updateBACommands As Command() = {baKeyVal, CR303000.Actions.ConverToCustomer, CR303000.Actions.Save}
That gets me past that line without an error, but then when I call the AR303000Submit it just creates a separate Customer record with a different Customer/Business Account ID rather than converting the existing Business Account.
There are two problems here:
An error occurred while processing the field Default Location value 15497 Error: Default Location '15497' cannot be found in the system.
I think this is your data problem. Login with browser and check this Business Account manually. I think you will receive same error.
Convert To Customer action problem
This action produce redirect. It is a problem. But there is a solution:
Create new customization Project
Create GraphExtension for Grapth "BusinessAccountMaint"
Insert next code
using System;
using System.Collections;
using Avalara.AvaTax.Adapter.AvaCert2Service;
using PX.Common;
using PX.Data;
using PX.Data.EP;
using PX.Objects.AP;
using PX.Objects.CS;
using PX.Objects.CT;
using PX.Objects.SO;
using PX.SM;
using System.Collections.Generic;
using PX.Objects;
using PX.Objects.CR;
namespace PX.Objects.CR
{
public class BusinessAccountMaint_Extension : PXGraphExtension
{
public PXAction<BAccount> convertToCustomerAndSave;
// hidden action. Used in API calls
[PXUIField(DisplayName = "Convert To Customer And Save", Visible = false, MapEnableRights = PXCacheRights.Select, MapViewRights = PXCacheRights.Select)]
[PXButton(ImageKey = PX.Web.UI.Sprite.Main.Process)]
public virtual IEnumerable ConvertToCustomerAndSave(PXAdapter adapter)
{
try
{
return Base.ConverToCustomer(adapter);
}
catch (PXRedirectRequiredException e) // catch redirect exception
{
(e.Graph as AR.CustomerMaint).Save.Press(); // Save our new customer
return adapter.Get();
}
}
}
}
Save and Publish
Regenerate Service Reference (WSDL)
Use new action in your cade
static void Main(string[] args)
{
var client = new ScreenSoapClient();
client.Login("admin", "123");
var baSchema = client.CR303000GetSchema();
var commands = new Command[]
{
new Value
{
Value = "MAURICES",
LinkedCommand = baSchema.AccountSummary.BusinessAccount
},
baSchema.Actions.ConvertToCustomerAndSave // use our new action instead of default
};
client.CR303000Submit(commands);
}
This code will convert Business Account to Customer and Save it immediately
I'm just starting to use Glimpse with my MVC5 project and have run into an issue when I use Postal to send an email without disabling Glimpse. I've been able to narrow it down to an issue with both packages - it doesn't occur if the Glimpse cookie has not been turned on.
In Fiddler, I checked the difference between the two. When it threw the exception, the cookie was
glimpsePolicy=On
when it worked (Glimpse was off) there were two cookies
glimpseId=FBar; glimpsePolicy=
The exception I get is
System.ArgumentNullException: Value cannot be null.
Parameter name: controllerContext
at System.Web.Mvc.ChildActionValueProviderFactory.GetValueProvider(ControllerContext controllerContext)
at Castle.Proxies.Invocations.ValueProviderFactory_GetValueProvider.InvokeMethodOnTarget()
at Castle.DynamicProxy.AbstractInvocation.Proceed()
at Glimpse.Core.Extensibility.ExecutionTimer.Time(Action action)
at Glimpse.Core.Extensibility.AlternateMethod.NewImplementation(IAlternateMethodContext context)
at Castle.DynamicProxy.AbstractInvocation.Proceed()
at Castle.Proxies.ValueProviderFactoryProxy.GetValueProvider(ControllerContext controllerContext)
at System.Web.Mvc.ValueProviderFactoryCollection.GetValueProvider(ControllerContext controllerContext)
at System.Web.Mvc.ControllerBase.get_ValueProvider()
at Glimpse.Mvc.Message.ActionMessageExtension.AsActionMessage[T](T message, ControllerBase controller)
at Glimpse.Mvc.AlternateType.ViewEngine.FindViews.PostImplementation(IAlternateMethodContext context, TimerResult timerResult)
at Glimpse.Core.Extensibility.AlternateMethod.NewImplementation(IAlternateMethodContext context)
at Castle.DynamicProxy.AbstractInvocation.Proceed()
at Castle.Proxies.IViewEngineProxy.FindView(ControllerContext controllerContext, String viewName, String masterName, Boolean useCache)
at System.Web.Mvc.ViewEngineCollection.<>c__DisplayClass6.<FindView>b__4(IViewEngine e)
at System.Web.Mvc.ViewEngineCollection.Find(Func`2 lookup, Boolean trackSearchedPaths)
at System.Web.Mvc.ViewEngineCollection.Find(Func`2 cacheLocator, Func`2 locator)
at Postal.EmailViewRenderer.Render(Email email, String viewName)
at Postal.EmailService.Send(Email email)
at System.Dynamic.UpdateDelegates.UpdateAndExecuteVoid1[T0](CallSite site, T0 arg0)
at System.Web.Mvc.ActionMethodDispatcher.<>c__DisplayClass1.<WrapVoidAction>b__0(ControllerBase controller, Object[] parameters)
at System.Web.Mvc.ReflectedActionDescriptor.Execute(ControllerContext controllerContext, IDictionary`2 parameters)
at System.Web.Mvc.ControllerActionInvoker.InvokeActionMethod(ControllerContext controllerContext, ActionDescriptor actionDescriptor, IDictionary`2 parameters)
at System.Web.Mvc.Async.AsyncControllerActionInvoker.<BeginInvokeSynchronousActionMethod>b__36(IAsyncResult asyncResult, ActionInvocation innerInvokeState)
at System.Web.Mvc.Async.AsyncResultWrapper.WrappedAsyncResult`2.CallEndDelegate(IAsyncResult asyncResult)
at Castle.Proxies.Invocations.AsyncControllerActionInvoker_EndInvokeActionMethod.InvokeMethodOnTarget()
at Castle.DynamicProxy.AbstractInvocation.Proceed()
at Glimpse.Mvc.AlternateType.AsyncActionInvoker.EndInvokeActionMethod.NewImplementation(IAlternateMethodContext context)
at Castle.DynamicProxy.AbstractInvocation.Proceed()
at Castle.Proxies.AsyncControllerActionInvokerProxy.EndInvokeActionMethod(IAsyncResult asyncResult)
at System.Web.Mvc.Async.AsyncControllerActionInvoker.AsyncInvocationWithFilters.<InvokeActionMethodFilterAsynchronouslyRecursive>b__3c()
at System.Web.Mvc.Async.AsyncControllerActionInvoker.AsyncInvocationWithFilters.<>c__DisplayClass45.<InvokeActionMethodFilterAsynchronouslyRecursive>b__3e()
at System.Web.Mvc.Async.AsyncControllerActionInvoker.<>c__DisplayClass30.<BeginInvokeActionMethodWithFilters>b__2f(IAsyncResult asyncResult)
at System.Web.Mvc.Async.AsyncControllerActionInvoker.<>c__DisplayClass1e.<>c__DisplayClass28.<BeginInvokeAction>b__19()
at System.Web.Mvc.Async.AsyncControllerActionInvoker.<>c__DisplayClass1e.<BeginInvokeAction>b__1b(IAsyncResult asyncResult)
I created a quick action to test it. The controller code is:
public void TestEmailExt()
{
var confirmationToken = "ConfirmationToken";
var Phone1 = "**********";
dynamic email = new Email("RegEmail");
email.To = "**#gmail.com";
email.UserName = "UserName";
email.ConfirmationToken = confirmationToken;
email.Phone = Extensions.Right(Phone1, 4);
if (email.To.Contains("#mydomain"))
email.From = INTERNAL_EMAIL_FROM;
else
email.From = EXTERNAL_EMAIL_FROM;
email.Send();
}
The reason this fails is because the Postal library creates its own HttpContext instance while rendering the email view as the decompiled CreateControllerContext method inside Postal's EmailViewRenderer class shows:
private ControllerContext CreateControllerContext()
{
HttpContextWrapper httpContextWrapper = new HttpContextWrapper(new HttpContext(new HttpRequest("", this.UrlRoot(), ""), new HttpResponse(TextWriter.Null)));
RouteData routeData = new RouteData();
routeData.Values["controller"] = (object) this.EmailViewDirectoryName;
return new ControllerContext(new RequestContext((HttpContextBase) httpContextWrapper, routeData), (ControllerBase) new EmailViewRenderer.StubController());
}
This means that the setup that Glimpse does at BeginRequest is completely removed, while the hooks are still in place to intercept MVC related calls.
We've had a similar issue where I gave a similar response to why this is not working.
UPDATE :
I mentioned above that a similar issue had been reported previously, but while I was trying to find a more appropriate solution, it seemed that this case is slightly different in that respect that the other similar issue actually executes a controller with the freshly created context resulting in a NullReferenceException in Glimpse specific code, while here we get a NullReferenceException inside MVC specific code, albeit triggered by Glimpse.
System.ArgumentNullException: Value cannot be null.
Parameter name: controllerContext
at System.Web.Mvc.ChildActionValueProviderFactory.GetValueProvider(ControllerContext controllerContext)
And the exception we get here is because the ControllerContext property on the StubController instance (created inline) is null, which would normally be set when executing the controller (which is not the case here).
So the workaround that I proposed below still applies, but can be avoided if the code of the CreateControllerContext() above is slightly modified:
private ControllerContext CreateControllerContext()
{
HttpContextWrapper httpContextWrapper = new HttpContextWrapper(new HttpContext(new HttpRequest("", this.UrlRoot(), ""), new HttpResponse(TextWriter.Null)));
RouteData routeData = new RouteData();
routeData.Values["controller"] = (object) this.EmailViewDirectoryName;
// MODIFIED
var stubController = new EmailViewRenderer.StubController();
var controllerContext = new ControllerContext(new RequestContext(httpContextWrapper, routeData), stubController);
stubController.ControllerContext = controllerContext;
return controllerContext;
}
I've created an issue for this on the Postal issue tracker
END OF UPDATE
I think the best solution, for now, is to disable Glimpse while calling into Postal and restore normal Glimpse behavior back again afterwards. We might include this one way or the other into the Glimpse Core library in one of the upcoming releases as it seems that disabling Glimpse during a specific part of the request processing logic doesn't seem to be that uncommon, but for now the following snippet might help you (beware it makes use of a Glimpse internal key which is not guaranteed to be there in an upcoming release)
public class GlimpseSuppressionScope : IDisposable
{
private const string GlimpseRequestRuntimePermissionsKey = "__GlimpseRequestRuntimePermissions";
private readonly HttpContext currentHttpContext;
private readonly RuntimePolicy? currentRuntimePolicy;
private bool disposed;
public GlimpseSuppressionScope(HttpContext currentHttpContext)
{
if (currentHttpContext == null)
{
throw new ArgumentNullException("currentHttpContext");
}
this.currentHttpContext = currentHttpContext;
this.currentRuntimePolicy = this.currentHttpContext.Items[GlimpseRequestRuntimePermissionsKey] as RuntimePolicy?;
this.currentHttpContext.Items[GlimpseRequestRuntimePermissionsKey] = RuntimePolicy.Off;
}
~GlimpseSuppressionScope()
{
this.Dispose(false);
}
public void Dispose()
{
this.Dispose(true);
GC.SuppressFinalize(this);
}
private void Dispose(bool disposing)
{
if (!this.disposed)
{
if (disposing)
{
if (this.currentHttpContext != null)
{
this.currentHttpContext.Items.Remove(GlimpseRequestRuntimePermissionsKey);
if (this.currentRuntimePolicy.HasValue)
{
this.currentHttpContext.Items[GlimpseRequestRuntimePermissionsKey] = this.currentRuntimePolicy.Value;
}
}
}
this.disposed = true;
}
}
}
which you can then use in your controller action method as shown below:
public void TestEmailExt()
{
using (new GlimpseSuppressionScope(System.Web.HttpContext.Current))
{
var confirmationToken = "ConfirmationToken";
var Phone1 = "**********";
dynamic email = new Email("RegEmail");
email.To = "**#gmail.com";
email.UserName = "UserName";
email.ConfirmationToken = confirmationToken;
email.Phone = Extensions.Right(Phone1, 4);
if (email.To.Contains("#mydomain"))
email.From = INTERNAL_EMAIL_FROM;
else
email.From = EXTERNAL_EMAIL_FROM;
email.Send();
}
}