请帮我解决这个问题。
嵌入在CRM on Demand中我有一个视图,需要从CRM输入字段中获取值,以通过Web服务对CRM进行搜索,并在找到重复记录时显示视图。
在这里,我将代码放入针对CRM {crm.context.ts
}的一些库中:
/*
* Context Helpers
*/
declare var epmcrm: any;
class context {
private getParameterByName(name) {
name = name.replace(/[\[]/, "\\[").replace(/[\]]/, "\\]");
var regex = new RegExp("[\\?&]" + name + "=([^&#]*)"),
results = regex.exec(location.search);
return results == null ? "" : decodeURIComponent(results[1].replace(/\+/g, " "));
}
config: { objects: { [key: string]: any } } = {
objects: {
"Homepage": {
name: "Homepage"
},
"Task": {
name: "Task",
idParam: "TaskDetailForm.Id",
screens: {
"/OnDemand/user/TaskDetail": "Detail",
"/OnDemand/user/TaskEdit": "Edit"
}
},
"Account": {
name: "Account",
idParam: "AccountDetailForm.Id",
screens: {
"/OnDemand/user/TaskDetail": "Detail",
"/OnDemand/user/TaskEdit": "Edit"
}
},
"User": {
name: "User",
idParam: "UserDetailForm.Id",
screens: {
"/OnDemand/user/UserDetail": "Detail",
"/OnDemand/user/UserEdit": "Edit"
}
},
"Opportunity": {
name: "Opportunity",
idParam: "OpportunityDetailForm.Id",
screens: {
"/OnDemand/user/OpportunityDetail": "Detail",
"/OnDemand/user/OpportunityEdit": "Edit"
}
},
"Contact": {
name: "Contact",
idParam: "ContactDetailForm.Id",
screens: {
"/OnDemand/user/ContactDetail": "Detail",
"/OnDemand/user/ContactEdit": "Edit",
// "/OnDemand/user/ContactInsert": "Create"
}
}
}
};
private knownPaths: { [key: string]: any } = {
"/OnDemand/user/Homepage": this.config.objects["Homepage"],
"/OnDemand/user/TaskDetail": this.config.objects["Task"],
"/OnDemand/user/TaskEdit": this.config.objects["Task"],
"/OnDemand/user/AccountDetail": this.config.objects["Account"],
"/OnDemand/user/AccountEdit": this.config.objects["Account"],
"/OnDemand/user/ContactDetail": this.config.objects["Contact"],
"/OnDemand/user/ContactEdit": this.config.objects["Contact"],
// "/OnDemand/user/ContactInsert": this.config.objects["Contact"],
"/OnDemand/user/UserDetail": this.config.objects["User"],
"/OnDemand/user/UserEdit": this.config.objects["User"],
"/OnDemand/user/OpportunityEdit": this.config.objects["Opportunity"]
//"/OnDemand/user/CustomObj2": mapping to custom objects here is important!
};
webServiceUrl: string = null;
screen: string = null;
objectType: string = null;
objectId: string = null;
ssoToken: string = null;
moduleRoot: string = null;
rowId: string = null;
commentsAction: string = null;
status: string = null;
//crm parameters to built the task link;
account: string = null;
accountId: string = null;
contact: string = null;
contactId: string = null;
quote: string = null;
quoteId: string = null;
order: string = null;
orderId: string = null;
oppty: string = null;
opptyId: string = null;
lead: string = null;
leadId: string = null;
step: string = null;
//crm contact
lastName: string = null;
firstName: string = null;
email: string = null;
constructor() {
// pick out the info from the url
this.webServiceUrl = "https://" + window.location.hostname + "/Services/Integration";
// get the SSO token from the global variable defined in the web applet
this.ssoToken = epmcrm.ssoToken;
// get the module root from the global variable defined in the web applet
this.moduleRoot = epmcrm.moduleRoot;
this.rowId = epmcrm.rowId;
this.commentsAction = epmcrm.commentsAction;
this.status = epmcrm.status;
this.step = epmcrm.step;
//crm parameters to built the task link;
this.account = epmcrm.account;
this.accountId = epmcrm.accountId;
this.contact = epmcrm.contact;
this.contactId = epmcrm.contactId;
this.quote = epmcrm.quote;
this.quoteId = epmcrm.quoteId;
this.order = epmcrm.order;
this.orderId = epmcrm.orderId;
this.oppty = epmcrm.oppty;
this.opptyId = epmcrm.opptyId;
this.lead = epmcrm.lead;
this.leadId = epmcrm.leadId;
//crm Contact
$("#ContactEditForm\\.First\\ Name").on("change", function () {
this.firstName = (<HTMLInputElement>document.getElementById("ContactEditForm.First Name")).value;
});
$("#ContactEditForm\\.Email\\ Address").on("change", function () {
this.email = (<HTMLInputElement>document.getElementById("ContactEditForm.Email Address")).value;
});
$("#ContactEditForm\\.Last\\ Name").on("change", function () {
this.lastName = (<HTMLInputElement>document.getElementById("ContactEditForm.Last Name")).value;
});
// attempt to discover contextual information
var pathname = window.location.pathname;
if (this.knownPaths[pathname]) {
var obj = this.knownPaths[pathname];
this.objectType = obj.name;
if (obj.idParam) {
this.objectId = this.getParameterByName(obj.idParam);
}
if (obj.screens) {
this.screen = obj.screens[pathname];
}
}
}
}
export = context;
In the view models I have what should give me the results into knockout observables which should than mirror CRM field and with this results I would perform a search and return or not some results:
`contactSearch.ts`
import ko = require("knockout");
import context = require("libs/crm.context");
import contacts = require("libs/crm.contacts");
$("#BTN_TB_ContactNewForm_Save").hide();
$("#BTN_TB_ContactNewForm_Save_idx_1").hide();
//$("#ContactEditForm\\.First\\ Name").on("change", assignFName);
//$("#ContactEditForm\\.Last\\ Name").on("change", assignLName);
//function assignFName() {
// var firstName = (<HTMLInputElement>document.getElementById("ContactEditForm.First Name")).value;
// alert(firstName);
//}
//function assignLName() {
// var lastName = (<HTMLInputElement>document.getElementById("ContactEditForm.Last Name")).value;
// alert(lastName);
//}
//function assignEmail() {
// var Email = (<HTMLInputElement>document.getElementById("ContactEditForm.Email Address")).value
// alert(Email);
//}
//var contactViewModel = function () {
// var self = this;
// self.validContacts = ko.observableArray([]);
// self.addContact = function (validContact) {
// self.validContacts.puch(validContact);
// $.ajax({
// data: ko.toJSON(this),
// contentType: 'application/json',
// success: function (result) {
// validContact.fName(result.
// }
// });
// }
//}
class contactSearch {
private _context: context = new context();
private _contacts: contacts = new contacts(this._context.webServiceUrl);
private _firstName = this._context.firstName;
private _lastName = this._context.lastName;
private _email = this._context.email;
vFName = ko.observable(this._firstName);
vLName = ko.observable(this._lastName);
vEmail = ko.observable(this._email);
//email = ko.computed({
// read: () => $("#ContactEditForm\\.Email\\ Address").on("change", function () {
// })
//})
////})
//lName = ko.observable("");
////email = ko.computed(function () {
//// assignEmail();
//})
isSearching: KnockoutObservable<boolean> = ko.observable(false);
searchValue = ko.computed({
read: () => ("[ContactEmail]~=" + "'" + "" + "'" + " AND [ContactFirstName]~=" + "'" + this.vFName() + "'" + " AND [ContactLastName]~=" + "'" + this.vLName() + "'")
});
contactSearchResults: KnockoutObservableArray<IContact> = ko.observableArray([]);
doValidation() {
$("#ContactEditForm\\.Email\\ Address").on("change", function () {
})
}
doContactSearch() {
this.isSearching(true);
this.contactSearchResults([]);
this._contacts
.find(this.searchValue(), ["Id", "ContactFirstName", "ContactLastName", "ContactEmail", "AccountId", "AccountName"])
.done((results: IContact[]) => {
if (results.length > 0) {
this.contactSearchResults(results);
this.isSearching(false);
}
else {
$("#BTN_TB_ContactNewForm_Save").show();
$("#BTN_TB_ContactNewForm_Save_idx_1").show();
alert("# of matching results= " + results.length);
}
});
}
bindTR(element): void {
/*
* Replicate the CRMOD method of hover styles
*/
var $element = $(element);
$element.hover(
() => {
$element.attr("_savedBGColor", $element.css("background-color"));
$element.css("background-color", "#d3dde6");
},
() => {
$element.css("background-color", $element.attr("_savedBGColor"));
$element.attr("_savedBGColor", "");
}
);
}
bindLink(element): void {
var $element = $(element);
$element.click(
() => {
window["doNavigate"]('ContactDetail?ocTitle=' + encodeURIComponent(this.vLName()) + '&ContactDetailForm.Id=' + this.contactSearchResults["Id"] + '&OCTYPE=', true, this, null)
},
() => {
$element.css("text-decoration", "underline");
}
);
}
}
export = contactSearch;
大卫,
我已经创建了observable并且我在HTML视图模型中绑定了这些,但我的数据源是那些HTMLInputElement,我不知道如何将值传递给observables。
<p>Email <input data-bind="value: vEmail" />
<span data-bind="text: vEmail"></span>
<span data-bind="text: vFName"></span>
<span data-bind="text: vLName"></span>
<p>Enter the search spec: <textarea data-bind="value: searchValue" />
<button type="button" data-bind="click: validation, click: doContactSearch">Go</button></p>
<table class="list clist" cellspacing="0">
<thead>
<tr>
<th class="m">
<th class="m">
<th>Id</th>
<th>First Name</th>
<th>Last Name</th>
<th>Email</th>
<th>Account Id</th>
<th>Account</th>
</tr>
</thead>
<tbody data-bind="visible: isSearching">
<tr>
<td colspan="99" style="text-align:center;">Searching, please wait...</td>
</tr>
</tbody>
<tbody data-bind="foreach: contactSearchResults, afterRender: bindTR, click: bindLink">
<tr>
<td class="lrml"> </td>
<td> </td>
<td data-bind="text: Id"></td>
<td data-bind="text: ContactFirstName"></td>
<td data-bind="text: ContactLastName"></td>
<td data-bind="text: ContactEmail"></td>
<td data-bind="text: AccountId"></td>
<td data-bind="text: AccountName"></td>
</tr>
</tbody>
</table>
我还有这个用CRM创建依赖关系的文件:
var epmcrm;
((epmcrm) => {
if (!epmcrm["moduleRoot"])
throw new Error("epmcrm global variable not configured");
require.config({
baseUrl: epmcrm.moduleRoot + "/scripts/app",
paths: {
// define the libs here
// 1. External
"jquery": "//cdnjs.cloudflare.com/ajax/libs/jquery/1.11.1/jquery.min",
"jquery-ui.theme": "//cdnjs.cloudflare.com/ajax/libs/jqueryui/1.11.2/jquery-ui.theme.css",// recently added
"knockout": "//cdnjs.cloudflare.com/ajax/libs/knockout/3.2.0/knockout-min",
"text": "//cdnjs.cloudflare.com/ajax/libs/require-text/2.0.10/text",
"json2": "//cdnjs.cloudflare.com/ajax/libs/json2/20130526/json2.min",
"knockout.mapping": "//cdnjs.cloudflare.com/ajax/libs/knockout.mapping/2.4.1/knockout.mapping", // added by daniel
// 2. Internal
"koExtensions": "../libs/knockout-extensions",
"libs/crm.tasks": "../libs/crm.tasks",
"libs/crm.accounts": "../libs/crm.accounts",
"libs/crm.contacts": "../libs/crm.contacts",
"libs/crm.users": "../libs/crm.users",
"libs/crm.session": "../libs/crm.session",
"libs/crm.context": "../libs/crm.context",
"libs/crm.objects": "../libs/crm.objects",
"libs/crm.utilities": "../libs/crm.utilities",
"libs/crm.viewEngine": "../libs/crm.viewEngine",
"libs/crm.viewmodelEngine": "../libs/crm.viewmodelEngine"
},
shim: {
"knockout": {
deps: ["json2"]
}
}
});
require(["knockout", "knockout.mapping", "koExtensions"],
(ko: KnockoutStatic, komap: KnockoutMapping) => {
ko.mapping = komap;
ko.applyBindings({}, document.getElementById("QuoteWebAppletContainer"));
});
})(epmcrm || (epmcrm = {}));