I have an issue adding some code in SAP cloud application.
I have to retrieve the ID of the employee that creates an order in C4C and print it in a camp z (or "label") called CreatedECC. When an emp creates this order a form is created where you can see emp name, date, delivery status, creation date, created by, etc... here is where the label was added for me to retrieve the userID and print it. Im not sure if someone can help me with the code... there is so much i can share.
Im new to javascript (and SAP cloud app) so i dont entirely understand the code and that´s why i need help
The code is:
import ABSL;
import AP.CRM.Global;
var query_mapping;
var sel_param_mapping;
var result_mapping;
this.IsConsistent = true;
var i = 0;
foreach (var item in this.Item)
{
if (!item.Plant.IsInitial())
{
item.Plant = item.Plant.ToUpperCase();
query_mapping = Plants.QueryByElements;
sel_param_mapping = query_mapping.CreateSelectionParams();
sel_param_mapping.Add(query_mapping.PlantID, "I", "EQ", item.Plant);
result_mapping = query_mapping.Execute(sel_param_mapping);
if (!result_mapping.GetFirst().IsSet())
{
raise MsgNoFoundPlantID.Create("E", item.Plant);
i = 1;
}
}
}
if (i == 1)
{
this.IsConsistent = false;
}
I spoke with a partner via skype (i think he helped with the development) and he told me the steps i need to follow wich are:
Create the patch in the corresponding development. Done.
Add a reference object and select the customizing camp that was created for you
Add your code so that a variable would be equal to the value Context.GetCurrentIdentityUUID. Through that value you get the userID you need to print in the customizing camp... And that is all
Related
So, I'm writing an app to 'flesh out' new clients in Rally. It will have tools to create templates which will add first:
add a 'Feature'
add 'UserStories' under that 'Feature'
add 'Tasks' under those 'UserStories' individually
I have figured out step 1. But how to associate anything I can't figure out from the horrible and cryptic documentation. Here's what I have so far:
var FeatureToAdd = _featureRepository.GetFeatures().FirstOrDefault(x => x.Id == 2);
// Initialize the REST API. You can specify a web service version if needed in the constructor.
RallyRestApi restApi = GetRallyRestApi();
//Create an item
DynamicJsonObject toCreate = new DynamicJsonObject();
toCreate["Name"] = FeatureToAdd.Name;
toCreate["Description"] = FeatureToAdd.Description;
// important to which this belongs, but I no ID I ever use works
//toCreate["Workspace"] = "/workspace/" + WebConfigurationManager.AppSettings["RallyAPIWorkspaceID"];
//toCreate["Project"] = "/project/XXXXX";
//toCreate["Iteration"] = "/iteration/XXXXXX";
// create feature - feature is under PortfolioItem
CreateResult createFeatureResult = restApi.Create("PortfolioItem/Feature", toCreate);
// scrape ID off the end of the reference
var pureId = createFeatureResult.Reference.Substring(createFeatureResult.Reference.LastIndexOf('/') + 1);
// add UserStories
foreach (UserStory u in FeatureToAdd.UserStories)
{
toCreate = new DynamicJsonObject();
toCreate["Name"] =u.Name;
toCreate["Description"] = u.Description;
toCreate["WorkProduct"] = "PortfolioItem/Feature/" + pureId;
//toCreate["WorkProduct"] = createFeatureResult.Reference;<- tried this too
// hierarchicalrequirement = UserStory
CreateResult createUserStoryResult = restApi.Create("hierarchicalrequirement", toCreate);
}
Running this creates both, but no association happens. I get a warning:
Ignored JSON element hierarchicalrequirement.WorkProduct during processing of this request.
Why did it arbitrarily ignore this?...
It ignored WorkProduct because WorkProduct is not a valid field on HierarchicalRequirement. The field you want to specify to set the feature parent of a story is called PortfolioItem.
toCreate["PortfolioItem"] = Ref.GetRelativeRef(createFeatureResult.Reference);
Also, object relationships are specified as in WSAPI as refs (/type/id) so you can just directly pass in the reference from the createFeatureResult.
Sorry you're finding the api to be frustrating. It definitely has some weird dark corners but once you use it a bit and get a feel for how the various domain objects are related I think you'll find it to be quite powerful and consistent.
I am running into an issue where items I am creating are being set to deleted and not showing up in QBO.
Here is my code:
OAuthRequestValidator oauthValidator = new OAuthRequestValidator(
accessToken, accessTokenSecret, GetApiConsumerKey(), GetApiConsumerKeySecret());
ServiceContext context = new ServiceContext(GetApiAppToken(),
realmID, IntuitServicesType.QBO, oauthValidator);
context.IppConfiguration.BaseUrl.Qbo = "https://sandbox-quickbooks.api.intuit.com/";
context.IppConfiguration.Message.Request.SerializationFormat = SerializationFormat.Json;
context.IppConfiguration.Message.Response.SerializationFormat = SerializationFormat.Json;
DataService dataService = new DataService(context);
Customer customer = new Customer();
customer.Active = true;
customer.GivenName = "Test";
customer.DisplayName = "Test";
customer.WebAddr = new WebSiteAddress();
customer.WebAddr.URI = "http://www.google.com";
customer = dataService.Add<Customer>(customer);
if (customer.status == EntityStatusEnum.Deleted)
{
// Gets to here every time.
}
Can anyone see what might be going wrong here that causes every created entity to be deleted? I also can't find them using search in the QBO UI.
EDIT
As requested, I am adding the JSON data being sent/recieved:
{// Sent JSON
"GivenName":"Martin",
"FamilyName":"Noreke",
"DisplayName":"Martin Noreke",
"WebAddr":{"URI":"http://www.google.com"}
}
{// Received JSON
"Customer":{
"Taxable":true,
"Job":false,
"BillWithParent":false,
"Balance":0,
"BalanceWithJobs":0,
"CurrencyRef":{"value":"USD","name":"United States Dollar"},
"PreferredDeliveryMethod":"Print",
"domain":"QBO",
"sparse":false,
"Id":"68",
"SyncToken":"0",
"MetaData":{"CreateTime":"2015-07-19T08:25:22-07:00","LastUpdatedTime":"2015-07-19T08:25:22-07:00"},
"GivenName":"Martin",
"FamilyName":"Noreke",
"FullyQualifiedName":"Martin Noreke",
"DisplayName":"Martin Noreke",
"PrintOnCheckName":"Martin Noreke",
"Active":true,
"WebAddr":{"URI":"http://www.google.com"},
"DefaultTaxCodeRef":{"value":"2"}},
"time":"2015-07-19T08:25:22.958-07:00"
}
From the JSON, it appears to be creating the customer correctly. However, I am not able to locate it in the sandbox account I am connecting to.
This is where I get to post the self deprecating story about how I wasn't paying attention.
While working with the API, I somehow created a second company. Even when clicking on the first company, Intuit remembers your last company and takes you straight there.
Using the gear menu to switch companies allowed me to get to the right company so that I could see my created data.
I feel quite silly right now... :/
currently I´m writing on a outlook plugin for syncing goolge contacts with outlook but I have to cover some special case:
When a contact gets deleted on google side, my application detects the missing contact and creates a new contact based on the contact info from the outlook one.
Is there a way to get an event or history from google that tells me a user deleted this contact(s)?
Edit 1:
Here is my code how I´m accessing the contacts (what is working FINE):
public GoogleAccessor()
{
var parameters = new OAuth2Parameters()
{
ClientId = CLIENTID,
ClientSecret = CLIENTSECRET,
RedirectUri = REDIRECTURI,
Scope = SCOPES
};
string url = OAuthUtil.CreateOAuth2AuthorizationUrl(parameters);
//An own webbrowser for processing the access tokens
IAuthorizationCodeProvider authcodeProvider = new Presentation.BrowserAuthorizationCodeProvider(new Presentation.BrowserAuthentificatorVM());
parameters.AccessCode = authcodeProvider.GetAuthorizationCode(url);
if(parameters.AccessCode == null)
throw new GoogleOAuthException("AccesCode returned 'null' and failed!");
OAuthUtil.GetAccessToken(parameters);
this._contactsRequest = new ContactsRequest(new RequestSettings(APPLICATIONNAME, parameters) {AutoPaging = true});
}
public IList<IContact> GetAllMappedContacts()
{
Feed<Google.Contacts.Contact> f = _contactsRequest.GetContacts();
this._feedUri = new Uri(f.AtomFeed.Feed);
var photoList = new List<PhotoObject>();
foreach (var entry in f.Entries)
{
var photoObject = GetContactPhoto(entry);
if(photoObject != null)
photoList.Add(photoObject);
}
_googleMapper = new GoogleMapper(f.Entries);
return _googleMapper.MapToLocalContacts();;
}
The thing about syncing in general is that syncing is normally meant to work in one direction.
Source Data -> Data Flow -> Received Data.
In this instance, Outlook is your source data and Google is your received data. All information needs to come from your source. Since this is an Outlook add-in you are creating my suggestion would be to add a button to your add-in ribbon. You can call the button whatever ever you like (maybe "dontSyncButton"), but it's purpose is going to be Categorization of your contact.
Make it so that that when a contact is selected and then the button is clicked, the contact is given a special categorization (perhaps "Dont Sync").
Now give some logic to your code that executes the sync, and have that logic decide whether to sync the contact. Also, give some logic to tell the program to delete the contact out of Google for you if the contacts contains the special category. Semi-Pseudo Code below:
if(contact.Categories.ToString() == "Dont Sync")
{
//Don't Sync Contact
If(googleContact.Exists())
{
//Delete contact from Google if it exist
googleContact.Delete();
}
}
else
{
//Sync Contact
}
It would be nice if Outlook had many modifiable properties that weren't visible to users, but since it does not this is really one of the best options I can think of. I do this to sync contacts from a shared Outlook folder to personal ones and it has worked well so far.
Hope this helps!
We are having an issue with searching a custom record through SuiteTalk. Below is a sample of what we are calling. The issue we are having is in trying to set up the search using the internalId of the record. The issue here lies in in our initial development account the internal id of this custom record is 482 but when we deployed it through the our bundle the record was assigned with the internal Id of 314. It would stand to reason that this internal id is not static in a site per site install so we wondered what property to set up to reference the custom record. When we made the record we assigned its “scriptId’ to be 'customrecord_myCustomRecord' but through suitetalk we do not have a “scriptId”. What is the best way for us to allow for this code to work in all environments and not a specific one? And if so, could you give an example of how it might be used.
Code (C#) that we are attempting to make the call from. We are using the 2013.2 endpoints at this time.
private SearchResult NetSuite_getPackageContentsCustomRecord(string sParentRef)
{
List<object> PackageSearchResults = new List<object>();
CustomRecord custRec = new CustomRecord();
CustomRecordSearch customRecordSearch = new CustomRecordSearch();
SearchMultiSelectCustomField searchFilter1 = new SearchMultiSelectCustomField();
searchFilter1.internalId = "customrecord_myCustomRecord_sublist";
searchFilter1.#operator = SearchMultiSelectFieldOperator.anyOf;
searchFilter1.operatorSpecified = true;
ListOrRecordRef lRecordRef = new ListOrRecordRef();
lRecordRef.internalId = sParentRef;
searchFilter1.searchValue = new ListOrRecordRef[] { lRecordRef };
CustomRecordSearchBasic customRecordBasic = new CustomRecordSearchBasic();
customRecordBasic.recType = new RecordRef();
customRecordBasic.recType.internalId = "314"; // "482"; //THIS LINE IS GIVING US THE TROUBLE
//customRecordBasic.recType.name = "customrecord_myCustomRecord";
customRecordBasic.customFieldList = new SearchCustomField[] { searchFilter1 };
customRecordSearch.basic = customRecordBasic;
// Search for the customer entity
SearchResult results = _service.search(customRecordSearch);
return results;
}
I searched all over for a solution to avoid hardcoding internalId's. Even NetSuite support failed to give me a solution. Finally I stumbled upon a solution in NetSuite's knowledgebase, getCustomizationId.
This returns the internalId, scriptId and name for all customRecord's (or customRecordType's in NetSuite terms! Which is what made it hard to find.)
public string GetCustomizationId(string scriptId)
{
// Perform getCustomizationId on custom record type
CustomizationType ct = new CustomizationType();
ct.getCustomizationTypeSpecified = true;
ct.getCustomizationType = GetCustomizationType.customRecordType;
// Retrieve active custom record type IDs. The includeInactives param is set to false.
GetCustomizationIdResult getCustIdResult = _service.getCustomizationId(ct, false);
foreach (var customizationRef in getCustIdResult.customizationRefList)
{
if (customizationRef.scriptId == scriptId) return customizationRef.internalId;
}
return null;
}
you can make the internalid as an external property so that you can change it according to environment.
The internalId will be changed only when you install first time into an environment. when you deploy it into that environment, the internalid will not change with the future deployments unless you choose Add/Rename option during deployment.
I have created a vsto application that calls a webservice. everything seems to work just fine, but i would like to extend the functionality to call the test service version of my production service.
code snippet that works that calls my test service.
//how do i change here to be dynamic?
npfunctions.finfunctions service = new npfunctions.finfunctions();
var Results = service.ValidateFoapal(index.ToArray(), fund.ToArray(), org.ToArray(), prog.ToArray(), acct.ToArray(), row.ToArray());
/* if their are no error then return a "Y" for success.*/
if (Results.Count() < 0) { return LocallErrorInd; }
/*well we have encountered errors lets adjust the spreadsheet to notify the user.*/
else{
//REMOVE ANY VISUAL ERRORS
Microsoft.Office.Interop.Excel.Range delRng = Globals.ThisAddIn.Application.Range["R:S"];
delRng.Delete(XlDeleteShiftDirection.xlShiftToLeft);
for (int i = 0; i < Results.Count(); i++)
{//set the error indicator
LocallErrorInd = "Y";
//account error:
if (Results[i].FVALJOR_FUND_WARNING == "Y")
{
Microsoft.Office.Interop.Excel.Range WrkRng = Globals.ThisAddIn.Application.Range[Results[i].FVALJOR_ROW];
WrkRng.Offset[0, 17].Value2 = "Invalid Account";
}
i have seen this post How can I dynamically switch web service addresses in .NET without a recompile?
but it requires me to change my config file i would really like to change the service variable to point to another location based on a variable and basically flip from prod to test on my command. as i see it right now it appears that i would have to duplicate the code but i know there has got to be a better way. i like it to be something like.
if (TestBtn.Checked == true)
{
npfunctions.finfunctions service = new npfunctions.finfunctions();
Results = service.ValidateFoapal(index.ToArray(), fund.ToArray(), org.ToArray(), prog.ToArray(), acct.ToArray(), row.ToArray());
}
if (PrdBtn.Checked == true)
{
prdFunctions.finfunctions service = new prdFunctions.finfunctions();
Results = service.ValidateFoapal(index.ToArray(), fund.ToArray(), org.ToArray(), prog.ToArray(), acct.ToArray(), row.ToArray());
}
/* if their are no error then return a "Y" for success.*/
if (Results.Count() < 0) { return LocallErrorInd; }
Does your service object not have a URL property?
2nd option, you can use a config file transformation so you do not need to manually change the settings(after the intial setup of course).
npfunctions.finfunctions service = new npfunctions.finfunctions();
if (TestBtn.Checked == true)
{
service.url="<testurl>";
}
else
{
service.url="<produrl>";
}
Results = service.ValidateFoapal(index.ToArray(), fund.ToArray(), org.ToArray(), prog.ToArray(), acct.ToArray(), row.ToArray());
In our test client we have a drop-down to select between dev or tst. We also have buttons to select proxy or net.tcp. (We have many different people using our service using different methods).
In the app.config the names of the endpoints correlate with different selectable options.
Eg. name="BasicHttpBinding_IInterface_PROXY_DEV"
You can then dynamically build up which endpoint you would like to use and go with that.