├── LICENSE.txt
├── README.md
└── Sdk.FetchXml.ts
/LICENSE.txt:
--------------------------------------------------------------------------------
1 | The MIT License (MIT)
2 |
3 | Copyright (c) 2016 Jim Daly
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
23 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # ClientSideFetchXmlObjectLibraries
2 | JavaScript and TypeScript libraries which provide an object model for Microsoft Dynamics CRM FetchXML Queries
3 |
4 | These libraries provide an object model to compose FetchXml queries using either JavaScript directly,
5 | or by using TypeScript.
6 | ## In this README
7 | * [Ordinary use cases for client-side fetchXml queries](#ordinary-use-cases-for-client-side-fetchxml-queries)
8 | * [Why these libraries?](#why-these-libraries)
9 | * [Convert from XML to object and back](#convert-from-xml-to-object-and-back)
10 | * [Why two separate libraries?](#why-two-separate-libraries)
11 | * [When to use these libraries?](#when-to-use-these-libraries)
12 | * [Examples](#examples)
13 | * [Why do some classes have a read-only hash property?](#why-do-some-classes-have-a-read-only-hash-property)
14 | * [How were these tested?](#how-were-these-tested)
15 | * [Why aren't these in the CRM SDK?](#why-arent-these-in-the-crm-sdk)
16 |
17 | ## Ordinary use cases for client-side fetchXml queries
18 | Typically developers will use the advanced find tool in the CRM web application to compose a query and then
19 | download the fetchxml definition of the query. They can then modify the query as needed and use the fetch.xsd
20 | schema from the SDK if they want to make sure that the edits they make are valid according to the schema. They
21 | can then include include the fetchxml query definition as a string within JavaScript functions in the application.
22 | This approach is effective and these libraries are not intended as a replacement for this proven approach.
23 |
24 | ## Why these libraries?
25 | These libraries are an experiment to provide a better development experience when a developer wants
26 | more flexibilty to compose a query programmatically. With the 2011 (SOAP) endpoint C# developers can use the
27 | [QueryExpression Class](https://msdn.microsoft.com/en-us/library/microsoft.xrm.sdk.query.queryexpression.aspx)
28 | to compose queries. With JavaScript, the [Sdk.Soap.js](https://code.msdn.microsoft.com/SdkSoapjs-9b51b99a) sample
29 | library provides an Sdk.Query.QueryExpression class which provides the same functionality.
30 |
31 | However, with the Microsoft Dynamics CRM Web API there is no similar object designed to compose queries
32 | programmatically. You can compose queries using the OData syntax
33 | (see [Query Data using the Web API](https://msdn.microsoft.com/en-us/library/gg334767.aspx)), but this doesn't
34 | yet provide all the capabilities of FetchXML. So these libraries were created in an effort to see whether providing
35 | a wrapper around the objects defined by the fetchXML could provide a better way to compose queries in code.
36 |
37 | Both of these libraries provide the same interface which allows for instantiating instances of objects defined
38 | in the FetchXML Schema and public properties to set the values. In addition, these libraries provide methods
39 | to set every property and add or remove objects from collections. These methods are chainable because they return
40 | the object that they are applied to.
41 |
42 | ## Convert from XML to object and back
43 | Both of these libraries provide a `Sdk.FetchXml.fetch.fromXml` static method which accept a fetchXML string and
44 | return an `Sdk.FetchXML.fetch` object with all the child objects contained within it. The
45 | `Sdk.FetchXml.fetch.toXml` method returns a string that is the valid fetchXml for the objects contained within it.
46 | So this is basically a way to deserialize and serialize the fetchXml into the `Sdk.FetchXml.fetch` object.
47 |
48 | ## Why two separate libraries?
49 | At the end of the day, both of these result in a JavaScript library. I wrote the JavaScript library first.
50 | Then I wrote the TypeScript version because more and more people have been asking for TypeScript libraries.
51 | Not having a lot of experience with TypeScript, I wanted to see how it could be used to get the same result
52 | I'm used to getting with plain old JavaScript. In the end, I was able to get the same interfaces but I had to apply some different strategies.
53 |
54 | For example, in JavaScript I prefer to return sealed objects because I want to eliminate the possiblity that people
55 | might add or remove the properties of the class instances. In Typescript I found I had to enable
56 | [Decorators](https://www.typescriptlang.org/docs/handbook/decorators.html) to get the behavior I wanted. So you will
57 | need to enable `experimentalDecorators` and use a tsconfig.json with this setting set to true. Also, in JavaScript I
58 | like to use [Object.freeze](https://msdn.microsoft.com/en-us/library/ff806186.aspx) for static objects I use for enumerations.
59 | Seems that TypeScript enumerations can only have number values, so I used decorators again to ensure that the properties
60 | for these object could not be modified.
61 |
62 | I certainly like that the IntelliSense provided for TypeScript is much more solid that the extremely fragile IntelliSense
63 | that the JavaScript language service provides in Visual Studio. But I think I'd need to build an full TypeScript application
64 | before it becomes my my preferred way to write JavaScript.
65 |
66 | ## When to use these libraries?
67 | These libraries are relatively large (3000+ lines of code) and even minified they are about 40KB. For the typical use
68 | case where a developer simply needs to configure a relatively static query, or just include a few variables, the approach
69 | described in [Ordinary use cases for client-side fetchXml queries](#ordinary-use-cases-for-client-side-fetchxml-queries)
70 | is still probably the most effective approach for client-side scripts.
71 |
72 | I expect that these libraries may be helpful when a developer needs to provide a user interface like the advanced find tool
73 | in the CRM application. I can imagine leveraging CRM metadata together with these libraries to create this experience.
74 | Or perhaps a developer will leverage the objects in this library to provide an IQueryable type interface specifically for
75 | Microsoft CRM queries? Or perhaps some other Node.js or Cordova application I can't even imagine.
76 |
77 | If you use these libraries, please let me know how you use them.
78 |
79 | ## Examples
80 | Looking at the example in the CRM SDK [Use FetchXML to construct a query](https://msdn.microsoft.com/en-us/library/gg328117.aspx).
81 | ```xml
82 |
83 |
84 |
85 |
86 |
87 |
88 |
89 |
90 |
91 |
92 |
93 | ```
94 | The following JavaScript produces the equivalent XML:
95 | ```javascript
96 | var ns = Sdk.FetchXml;
97 | var q = ns.fetch(
98 | ns.entity("account")
99 | .addAttribute("accountid")
100 | .addAttribute("name")
101 | .addLinkEntity(
102 | ns.linkEntity("systemuser",null,"owninguser")
103 | .addFilter(
104 | ns.filter(ns.FilterType.And)
105 | .addCondition(
106 | ns.condition(
107 | "lastname",
108 | ns.Operator.NotEqual,
109 | [ns.value("Cannon")]
110 | )
111 | )
112 | )
113 | )
114 | )
115 | console.log(q.toXml());
116 | ```
117 | Note that specifying a namespace variable, in this case `ns` means less typing. Also notice that using the `new` keyword
118 | is optional when instantiating classes. The classes are defined so that they will still work if you forget to use it.
119 |
120 | The enumerations return string values. You can use string values instead of the enumerations if you know them, but they must match the
121 | value of an enumeration. i.e. Use either `Sdk.FetchXml.FilterType.And` or just `and`.
122 |
123 | Also note the exclusive use of the chained add* methods to compose the object. The same query could also be composed this way:
124 | ```javascript
125 | var ns = Sdk.FetchXml;
126 | var condition = ns.condition("lastname", ns.Operator.NotEqual, [ns.value("Cannon")]);
127 | var filter = ns.filter(ns.FilterType.And);
128 | filter.conditions = [condition];
129 | var linkEntity = ns.linkEntity("systemuser");
130 | linkEntity.to = "owninguser";
131 | linkEntity.filters = [filter];
132 | var entity = ns.entity("account", [ns.attribute("accountid"), ns.attribute("name")]);
133 | entity.linkEntities = [linkEntity];
134 | var q = ns.fetch(entity);
135 | console.log(q.toXml());
136 | ```
137 | But I think this style is difficult to read. But these can also be used in combination:
138 | ```javascript
139 | var ns = Sdk.FetchXml;
140 | var condition = ns.condition("lastname", ns.Operator.NotEqual, [ns.value("Cannon")]);
141 |
142 | var filter = ns.filter(ns.FilterType.And)
143 | .addCondition(condition);
144 |
145 | var linkEntity = ns.linkEntity("systemuser",null,"owninguser")
146 | .addFilter(filter);
147 |
148 | var entity = ns.entity("account", [ns.attribute("accountid"), ns.attribute("name")])
149 | .addLinkEntity(linkEntity);
150 |
151 | var q = ns.fetch(entity);
152 | console.log(q.toXml());
153 | ```
154 |
155 | All values must be set using an array, even when there is just a single value. If it is a single value, the XML will set
156 | the value as an attribute on the condition. If multiple values are used, they will result in separate child `value` elements
157 | of the condition element.
158 |
159 | TypeScript is very similar to JavaScript except that you must use the `new` keyword.
160 | ```typescript
161 | var ns = Sdk.FetchXml;
162 | var q = new ns.fetch(
163 | new ns.entity("account")
164 | .addAttribute("accountid")
165 | .addAttribute("name")
166 | .addLinkEntity(
167 | new ns.linkEntity("systemuser",null,"owninguser")
168 | .addFilter(
169 | new ns.filter(ns.FilterType.And)
170 | .addCondition(
171 | new ns.condition(
172 | "lastname",
173 | ns.Operator.NotEqual,
174 | [new ns.value("Cannon")]
175 | )
176 | )
177 | )
178 | )
179 | );
180 | console.log(q.toXml());
181 | ```
182 | ## Why do some classes have a read-only hash property?
183 | In order to implement methods to add or remove items from a collection it was challenging to identify which specific item
184 | to remove. If you had an instance of an object used in a query that would match using a `===` operator, you can detect it
185 | and remove it by reference. But if you add an object using the chaining methods you wouldn't have a reference and none of these
186 | objects have a unique identifier property. So I found some code on stack overflow
187 | [Generate a Hash from string in Javascript/jQuery](http://stackoverflow.com/questions/7616461/generate-a-hash-from-string-in-javascript-jquery)
188 | which cited this source [Javascript implementation of Java’s String.hashCode() method](http://werxltd.com/wp/2010/05/13/javascript-implementation-of-javas-string-hashcode-method/)
189 | Using this extension to the String.prototype, I implemented a read-only hash property that seems to uniquely match the available
190 | property values for each object. Using this property, I implemented various `remove*` methods that will remove a matching object from a reference
191 | when you don't happen to have a reference to it. There are also various `remove*ByRef` methods you can use if you do have a reference
192 | to an item in a collection.
193 | For `Sdk.FetchXml.entity`, `Sdk.FetchXml.linkEntity` and `Sdk.FetchXml.condition`, there are `removeAttributeByName` and `removeValueByValue` methods
194 | because it seems that people will want to remove attributes or values based on the name or value directly.
195 |
196 | ## How were these tested?
197 | To test these I wrote a script to retrieve the fetchXML for all the system views (savedquery entity) and pass the string to the
198 | `Sdk.FetchXml.fetch.fromXml` method to instantiate the object. Then I called the `toXml` method on that instantiated object.
199 | After a few normalization adjustments, I compared the length of the strings to make sure they were identical.
200 | Most of the normalization adjustments had to do with inconsistent closing of elements, whether default attribute values were set,
201 | and different ways to set boolean values.
202 | The following is the function I used that highlight where differences were found that had no impact on the query defined:
203 | ```javascript
204 | function normalizeStrings(str) {
205 |
206 | if (str.indexOf(" distinct=\"false\"") > -1) {
207 | str = str.replace(" distinct=\"false\"", "");
208 | }
209 |
210 | if (str.indexOf("\">") > -1) {
211 | str = str.replace("\">", "\" />");
212 | }
213 |
214 | if (str.indexOf("\">") > -1) {
215 | str = str.replace("\">", "\" />");
216 | }
217 |
218 | if (str.indexOf("\">") > -1) {
219 | str = str.replace("\">", "\" />");
220 | }
221 |
222 | if (str.indexOf("isquickfindfields=\"1\"") > -1) {
223 | str = str.replace("isquickfindfields=\"1\"", "isquickfindfields=\"true\"");
224 | }
225 |
226 | if (str.indexOf("") > -1) {
227 | str = str.replace("", "");
228 | }
229 |
230 | if (str.indexOf("") > -1) {
231 | str = str.replace("", "");
232 | }
233 |
234 | if (str.indexOf(" descending=\"false\"") > -1) {
235 | str = str.replace(" descending=\"false\"", "");
236 | }
237 | return str;
238 | }
239 | ```
240 |
241 | ## Why aren't these in the CRM SDK?
242 | A combination of reasons:
243 | * It isn't known whether people are interested in this style of composing queries. If we publish them in the SDK it would
244 | seem like this is something the CRM product team thinks people want and need. You might start seeing questions about it on
245 | certification exams.
246 | * I wrote these on my own time just as an experiment. If I include them in the SDK we are obligated to maintain them.
247 | * I used some code I found on stack overflow to implement hash values for classes which may be in a collection.
248 | (See [Why do some classes have a read-only hash property?](#why-do-some-classes-have-a-read-only-hash-property))
249 | This is not allowed for official Microsoft samples.
250 | * I would like to share these with the community. If you have an enhancement, GitHub makes it easy for you to contribute to it or fork it.
251 |
--------------------------------------------------------------------------------
/Sdk.FetchXml.ts:
--------------------------------------------------------------------------------
1 | /*
2 | The MIT License (MIT)
3 |
4 | Copyright (c) 2016 Jim Daly
5 |
6 | Permission is hereby granted, free of charge, to any person obtaining a copy
7 | of this software and associated documentation files (the "Software"), to deal
8 | in the Software without restriction, including without limitation the rights
9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10 | copies of the Software, and to permit persons to whom the Software is
11 | furnished to do so, subject to the following conditions:
12 |
13 | The above copyright notice and this permission notice shall be included in all
14 | copies or substantial portions of the Software.
15 |
16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
22 | SOFTWARE.
23 | */
24 |
25 | namespace Sdk.FetchXml {
26 | @sealed
27 | export class attribute {
28 | /**
29 | * Contains the data for a fetchXml attribute element.
30 | * @param name The logical name of the attribute
31 | */
32 | constructor(name: string) {
33 | //new keyword not required
34 | if (!(this instanceof attribute))
35 | { return new attribute(name) }
36 |
37 | this.name = name;
38 | }
39 |
40 | private _name: string;
41 | private _build: Build = null;
42 | private _addedBy: string = null;
43 | private _alias: string = null;
44 | private _aggregate: Aggregate = null;
45 | private _groupBy: boolean = null;
46 | private _dateGrouping: DateGrouping = null;
47 | private _userTimeZone: boolean = null;
48 |
49 | /**
50 | *Gets or sets logical name of the attribute
51 | */
52 | public get name(): string {
53 | return this._name;
54 | }
55 | public set name(value: string) {
56 | if (!Util.isString(value)) {
57 | throw new Error("Sdk.FetchXml.attribute name property must be an string.");
58 | }
59 | this._name = value;
60 | }
61 | /**
62 | *Gets or sets the build of the attribute
63 | */
64 | public get build(): Build {
65 | return this._build;
66 | }
67 | public set build(value: Build) {
68 | if (!Util.isEnumMemberOrNull(Build, value)) {
69 | throw new Error("Sdk.FetchXml.attribute build property must be an Sdk.FetchXml.Build value or null.");
70 | }
71 | this._build = value;
72 | }
73 | /**
74 | *Gets or sets the addedBy property of the attribute
75 | */
76 | public get addedBy(): string {
77 | return this._addedBy;
78 | }
79 | public set addedBy(value: string) {
80 | if (!Util.isStringOrNull(value)) {
81 | throw new Error("Sdk.FetchXml.attribute addedBy property must be an string value or null.");
82 | }
83 | this._addedBy = value;
84 | }
85 | /**
86 | *Gets or sets the alias property of the attribute
87 | */
88 | public get alias(): string {
89 | return this._alias;
90 | }
91 | public set alias(value: string) {
92 | if (!Util.isStringOrNull(value)) {
93 | throw new Error("Sdk.FetchXml.attribute alias property must be an string value or null.");
94 | }
95 | this._alias = value;
96 | }
97 | /**
98 | *Gets or sets the aggregate property of the attribute
99 | */
100 | public get aggregate(): Aggregate {
101 | return this._aggregate;
102 | }
103 | public set aggregate(value: Aggregate) {
104 | if (!Util.isEnumMemberOrNull(Aggregate, value)) {
105 | throw new Error("Sdk.FetchXml.attribute aggregate property must be an Sdk.FetchXml.Aggregate value or null.");
106 | }
107 | this._aggregate = value;
108 | }
109 | /**
110 | *Gets or sets the groupBy property of the attribute
111 | */
112 | public get groupBy(): boolean {
113 | return this._groupBy;
114 | }
115 | public set groupBy(value: boolean) {
116 | if (!Util.isBooleanOrNull(value)) {
117 | throw new Error("Sdk.FetchXml.attribute groupBy property must be an boolean value or null.");
118 | }
119 | this._groupBy = value;
120 | }
121 | /**
122 | * Gets or sets the dateGrouping property of the attribute
123 | */
124 | public get dateGrouping(): DateGrouping {
125 | return this._dateGrouping;
126 | }
127 | public set dateGrouping(value: DateGrouping) {
128 | if (!Util.isEnumMemberOrNull(DateGrouping, value)) {
129 | throw new Error("Sdk.FetchXml.attribute dateGrouping property must be an Sdk.FetchXml.DateGrouping value or null.");
130 | }
131 | this._dateGrouping = value;
132 | }
133 | /**
134 | *Gets or sets the userTimeZone property of the attribute
135 | */
136 | public get userTimeZone(): boolean {
137 | return this._userTimeZone;
138 | }
139 | public set userTimeZone(value: boolean) {
140 | if (!Util.isBooleanOrNull(value)) {
141 | throw new Error("Sdk.FetchXml.attribute userTimeZone property must be an boolean value or null.");
142 | }
143 | this._userTimeZone = value;
144 | }
145 |
146 | /** @description Sets the name property of the attribute attribute
147 | * @param {string} name The name value to apply to the attribute
148 | * @returns {Sdk.FetchXml.attribute}
149 | */
150 | public setName(name: string) {
151 | this.name = name;
152 | return this;
153 | }
154 |
155 | /** @description Sets the build property of the build attribute
156 | * @param {Sdk.FetchXml.Build | null} build The build value to apply to the attribute
157 | * @returns {Sdk.FetchXml.attribute}
158 | */
159 | public setBuild(build?: Build) {
160 | (build) ? this.build = build : this.build = null;
161 | return this;
162 | }
163 |
164 | /** @description Sets the addedBy property of the attribute attribute
165 | * @param {string | null} addedBy The addedBy value to apply to the attribute
166 | * @returns {Sdk.FetchXml.attribute}
167 | */
168 | public setAddedBy(addedBy?: string) {
169 | (addedBy) ? this.addedBy = addedBy : this.addedBy = null;
170 | return this;
171 | }
172 |
173 | /** @description Sets the alias property of the attribute attribute
174 | * @param {string} alias The alias value to apply to the attribute
175 | * @returns {Sdk.FetchXml.attribute}
176 | */
177 | public setAlias(alias?: string) {
178 | (alias) ? this.alias = alias : this.alias = null;
179 | return this;
180 | }
181 |
182 | /** @description Sets the aggregate property of the attribute attribute
183 | * @param {Sdk.FetchXml.Aggregate | null } aggregate The aggregate value to apply to the attribute
184 | * @returns {Sdk.FetchXml.attribute}
185 | */
186 |
187 | public setAggregate(aggregate?: Aggregate) {
188 | (aggregate) ? this.aggregate = aggregate : this.aggregate = null;
189 | return this;
190 | }
191 | /** @description Sets the groupBy property of the attribute attribute
192 | * @param {boolean | null} groupBy The groupBy value to apply to the attribute
193 | * @returns {Sdk.FetchXml.attribute}
194 | */
195 |
196 | public setGroupBy(groupBy?: boolean) {
197 | (groupBy) ? this.groupBy = groupBy : groupBy = null;
198 | return this;
199 | }
200 |
201 | /** @description Sets the dateGrouping property of the attribute attribute
202 | * @param {Sdk.FetchXml.DateGrouping | null} dateGrouping The dateGrouping value to apply to the attribute
203 | * @returns {Sdk.FetchXml.attribute}
204 | */
205 | public setDateGrouping(dateGrouping?: DateGrouping) {
206 | (dateGrouping) ? this.dateGrouping = dateGrouping : this.dateGrouping = null;
207 | return this;
208 | }
209 |
210 | /** @description Sets the userTimeZone property of the attribute attribute
211 | * @param {boolean | null} userTimeZone The userTimeZone value to apply to the attribute
212 | * @returns {Sdk.FetchXml.attribute}
213 | */
214 | public setUserTimeZone(userTimeZone?: boolean) {
215 | (userTimeZone) ? this.userTimeZone = userTimeZone : this.userTimeZone = null;
216 | return this;
217 | }
218 |
219 | //Internal use only
220 | toXml(doc: XMLDocument): Node {
221 | var aNode = doc.createElement("attribute");
222 | aNode.setAttribute("name", this.name);
223 | if (this.build) {
224 | aNode.setAttribute("build", this.build);
225 | }
226 | if (this.addedBy) {
227 | aNode.setAttribute("addedby", this.addedBy);
228 | }
229 | if (this.alias) {
230 | aNode.setAttribute("alias", this.alias);
231 | }
232 | if (this.aggregate) {
233 | aNode.setAttribute("aggregate", this.aggregate);
234 | }
235 | if (Util.isBoolean(this.groupBy)) {
236 | aNode.setAttribute("groupby", (this.groupBy) ? "true" : "false");
237 | }
238 | if (this.dateGrouping) {
239 | aNode.setAttribute("dategrouping", this.dateGrouping);
240 | }
241 | if (Util.isBoolean(this.userTimeZone)) {
242 | aNode.setAttribute("usertimezone", (this.userTimeZone) ? "true" : "false");
243 | }
244 | return aNode;
245 | }
246 |
247 | //Internal use only
248 | static attributeFromXml(xml) {
249 | var attObj = new attribute(xml.attributes.getNamedItem("name").nodeValue);
250 |
251 | Util.parseAttributes(xml, attObj, (attObj, name, value) => {
252 | switch (name) {
253 | case "build":
254 | case "alias":
255 | case "aggregate":
256 | attObj[name] = value;
257 | break;
258 | case "addedby":
259 | attObj.addedBy = value;
260 | break;
261 | case "dategrouping":
262 | attObj.dateGrouping = value;
263 | break;
264 | case "groupby":
265 | attObj.groupBy = Util.convertFetchBoolType(value);
266 | case "usertimezone":
267 | attObj.userTimeZone = Util.convertFetchBoolType(value);
268 | break;
269 | default:
270 | break;
271 |
272 | }
273 | })
274 |
275 | return attObj;
276 | }
277 | }
278 | @sealed
279 | export class condition {
280 | /**
281 | * Contains the data for a fetchXml condition element.
282 | * @param attribute The attribute to evaluate in the condition
283 | * @param operator The operator to use when evaluating the attribute
284 | * @param [values] The value(s) to apply in the comparison.
285 | */
286 | constructor(attribute: string, operator: Sdk.FetchXml.Operator, values?: Array) {
287 | //New keyword not required in JS
288 | if (!(this instanceof Sdk.FetchXml.condition))
289 | { return new Sdk.FetchXml.condition(attribute, operator, values) }
290 |
291 | if (attribute && operator) {
292 | this.attribute = attribute;
293 | this.operator = operator;
294 | }
295 | else {
296 | throw new Error("Sdk.FetchXml.condition constructor parameters attribute and operator are required.")
297 | }
298 | if (values)
299 | this.values = values;
300 | }
301 |
302 | private _aggregate: Sdk.FetchXml.Aggregate = null;
303 | private _alias: string = null;
304 | private _attribute: string = null;
305 | private _column: string = null;
306 | private _entityname: string = null;
307 | private _operator: Sdk.FetchXml.Operator = null;
308 | private _rowAggregate: Sdk.FetchXml.RowAggregate = null;
309 | private _uihidden: boolean = null;
310 | private _uiname: string = null;
311 | private _uitype: string = null;
312 | private _values: Array = [];
313 |
314 | /**
315 | * Gets or sets the aggregate value to apply to the condition.
316 | */
317 | public get aggregate(): Sdk.FetchXml.Aggregate {
318 | return this._aggregate;
319 | }
320 | public set aggregate(value: Sdk.FetchXml.Aggregate) {
321 | this._aggregate = value;
322 | }
323 | /**
324 | * Gets or sets the alias value to apply to the condition.
325 | */
326 | public get alias(): string {
327 | return this._alias;
328 | }
329 | public set alias(value: string) {
330 | this._alias = value;
331 | }
332 | /**
333 | * Gets or sets the attribute value to apply to the condition.
334 | */
335 | public get attribute(): string {
336 | return this._attribute;
337 | }
338 | public set attribute(value: string) {
339 | this._attribute = value;
340 | }
341 | /**
342 | * Gets or sets the column attribute value to apply to the condition.
343 | */
344 | public get column(): string {
345 | return this._column;
346 | }
347 | public set column(value: string) {
348 | this._column = value;
349 | }
350 | /**
351 | * Gets or sets the entityname attribute value to apply to the condition.
352 | */
353 | public get entityname(): string {
354 | return this._entityname;
355 | }
356 | public set entityname(value: string) {
357 | this._entityname = value;
358 | }
359 | /**
360 | * Gets or sets the operator attribute value to apply to the condition.
361 | */
362 | public get operator(): Sdk.FetchXml.Operator {
363 | return this._operator;
364 | }
365 | public set operator(value: Sdk.FetchXml.Operator) {
366 | this._operator = value;
367 | }
368 | /**
369 | * Gets or sets the rowAggregate attribute value to apply to the condition.
370 | */
371 | public get rowAggregate(): Sdk.FetchXml.RowAggregate {
372 | return this._rowAggregate;
373 | }
374 | public set rowAggregate(value: Sdk.FetchXml.RowAggregate) {
375 | this._rowAggregate = value;
376 | }
377 | /**
378 | * Gets or sets the uihidden attribute value to apply to the condition.
379 | */
380 | public get uihidden(): boolean {
381 | return this._uihidden;
382 | }
383 | public set uihidden(value: boolean) {
384 | this._uihidden = value;
385 | }
386 | /**
387 | * Gets or sets the uiname attribute value to apply to the condition.
388 | */
389 | public get uiname(): string {
390 | return this._uiname;
391 | }
392 | public set uiname(value: string) {
393 | this._uiname = value;
394 | }
395 | /**
396 | * Gets or sets the uitype attribute value to apply to the condition.
397 | */
398 | public get uitype(): string {
399 | return this._uitype;
400 | }
401 | public set uitype(value: string) {
402 | this._uitype = value;
403 | }
404 | /**
405 | * Gets or sets the array of values to be applied to the query results
406 | */
407 | public get values(): Array {
408 | return this._values;
409 | }
410 | public set values(value: Array) {
411 | if (!Sdk.FetchXml.Util.isValueArrayOrNull(value)) {
412 | throw new Error("Sdk.FetchXml.condition.values must be an array of Sdk.FetchXml.value or null.")
413 | }
414 | if (value == null) {
415 | this._values = [];
416 | } else {
417 | this._values = value;
418 | }
419 | }
420 | //Internal use only
421 | public get hash(): string {
422 | var s = this._attribute.concat(this._operator,
423 | (this._aggregate ? this._aggregate : ""),
424 | (this._alias ? this._alias : ""),
425 | (this._column ? this._column : ""),
426 | (this._entityname ? this._entityname : ""),
427 | (this._rowAggregate ? this._rowAggregate : ""),
428 | (Sdk.FetchXml.Util.isNullOrUndefined(this._uihidden) ? "" : this._uihidden.toString()),
429 | (this._uiname ? this._uiname : ""),
430 | (this._uitype ? this._uitype : ""),
431 | Sdk.FetchXml.Util.getCollectionHash(this._values)
432 | );
433 | return s.hashCode();
434 | }
435 |
436 | /** @description Sets the value of the condition attribute
437 | * @param {string} attribute The attribute to evaluate in the condition.
438 | * @returns {Sdk.FetchXml.condition}
439 | */
440 | public setAttribute(attributeName) {
441 | this.attribute = attributeName;
442 | return this;
443 | }
444 |
445 | /** @description Sets the value of the condition attribute
446 | * @param {Sdk.FetchXml.Operator} operator The operator to use when evaluating the attribute.
447 | * @returns {Sdk.FetchXml.condition}
448 | */
449 | public setOperator(operator) {
450 | this.operator = operator;
451 | return this;
452 | }
453 |
454 | /** @description Sets the value of the condition operator
455 | * @param {Array} values The the value(s) to apply in the comparison.
456 | * @returns {Sdk.FetchXml.condition}
457 | */
458 | public setValues(values) {
459 | this.values = values;
460 | return this;
461 | }
462 |
463 | /** @description Adds a value to the values to apply in the comparison
464 | * @param {Sdk.FetchXml.value | any} value The the value to add to the values.
465 | * @returns {Sdk.FetchXml.condition}
466 | */
467 | public addValue(value) {
468 | if (Sdk.FetchXml.Util.isValue(value)) {
469 | this.values.push(value);
470 | }
471 | else {
472 | this.values.push(new Sdk.FetchXml.value(value));
473 | }
474 | return this;
475 | }
476 |
477 | /** @description Removes any values from the values collection by reference
478 | * @param {Sdk.FetchXml.value} value The value to remove from the values collection
479 | * @returns {Sdk.FetchXml.condition}
480 | */
481 | public removeValueByRef(value) {
482 | if (!Sdk.FetchXml.Util.isValue(value)) {
483 | throw new Error("Sdk.FetchXml.condition removeValueByRef method value parameter must be an Sdk.FetchXml.value.")
484 | }
485 | Sdk.FetchXml.Util.removeCollectionValueByRef(this.values, value);
486 | return this;
487 | }
488 |
489 | /** @description Removes all matching values from the values collection
490 | * @param {Sdk.FetchXml.value} value The value to remove from the values collection
491 | * @returns {Sdk.FetchXml.condition}
492 | */
493 | public removeValue(value) {
494 | if (!Sdk.FetchXml.Util.isValue(value)) {
495 | throw new Error("Sdk.FetchXml.condition removeValue method value parameter must be an Sdk.FetchXml.value.")
496 | }
497 | Sdk.FetchXml.Util.removeCollectionValue(this.values, value);
498 | return this;
499 | }
500 |
501 | /** @description Removes all any values from the values collection with the specified value property
502 | * @param {object} value The value to remove from the values collection
503 | * @returns {Sdk.FetchXml.condition}
504 | */
505 | public removeValueByValue(value) {
506 | Sdk.FetchXml.Util.removeCollectionValueByProperty(this.values, "value", value);
507 | return this;
508 | }
509 |
510 | /** @description Sets the Aggregate to apply in the condition
511 | * @param {Sdk.FetchXml.Aggregate} aggregate The Aggregate to apply in the condition
512 | * @returns {Sdk.FetchXml.condition}
513 | */
514 | public setAggregate(aggregate) {
515 | this.aggregate = aggregate;
516 | return this;
517 | }
518 |
519 | /** @description Sets the Alias to apply in the condition
520 | * @param {string} alias The alias to apply in the condition
521 | * @returns {Sdk.FetchXml.condition}
522 | */
523 | public setAlias(alias) {
524 | this.alias = alias;
525 | return this;
526 | }
527 |
528 | /** @description Sets the Column to apply in the condition
529 | * @param {string} column The column to apply in the condition
530 | * @returns {Sdk.FetchXml.condition}
531 | */
532 | public setColumn(column) {
533 | this.column = column;
534 | return this;
535 | }
536 |
537 | /** @description Sets the entityname to apply in the condition
538 | * @param {string} entityname The entityname to apply in the condition
539 | * @returns {Sdk.FetchXml.condition}
540 | */
541 | public setEntityname(entityname) {
542 | this.entityname = entityname;
543 | return this;
544 | }
545 |
546 | /** @description Sets the rowAggregate to apply in the condition
547 | * @param {Sdk.FetchXml.RowAggregate} rowAggregate The rowAggregate to apply in the condition
548 | * @returns {Sdk.FetchXml.condition}
549 | */
550 | public setRowAggregate(rowAggregate) {
551 | this.rowAggregate = rowAggregate;
552 | return this;
553 | }
554 |
555 | /** @description Sets the uihidden to apply in the condition
556 | * @param {boolean | null} uihidden The uihidden to apply in the condition
557 | * @returns {Sdk.FetchXml.condition}
558 | */
559 | public setUIhidden(uihidden) {
560 | this.uihidden = uihidden;
561 | return this;
562 | }
563 |
564 | /** @description Sets the uiname to apply in the condition
565 | * @param {string} uihidden The uiname to apply in the condition
566 | * @returns {Sdk.FetchXml.condition}
567 | */
568 | public setUIname(uiname) {
569 | this.uiname = uiname;
570 | return this;
571 | }
572 |
573 | /** @description Sets the uitype to apply in the condition
574 | * @param {string} uitype The uitype to apply in the condition
575 | * @returns {Sdk.FetchXml.condition}
576 | */
577 | public setUItype(uitype) {
578 | this.uitype = uitype;
579 | return this;
580 | }
581 |
582 | //Internal use only
583 | toXml(doc: XMLDocument): Node {
584 |
585 | var cNode = doc.createElement("condition");
586 | if (this.aggregate) {
587 | cNode.setAttribute("aggregate", this.aggregate)
588 | }
589 | if (this.alias) {
590 | cNode.setAttribute("alias", this.alias)
591 | }
592 | if (this.attribute) {
593 | cNode.setAttribute("attribute", this.attribute)
594 | }
595 | if (this.column) {
596 | cNode.setAttribute("column", this.column)
597 | }
598 | if (this.entityname) {
599 | cNode.setAttribute("entityname", this.entityname)
600 | }
601 | if (this.operator) {
602 | cNode.setAttribute("operator", this.operator)
603 | }
604 | if (this.rowAggregate) {
605 | cNode.setAttribute("rowAggregate", this.rowAggregate)
606 | }
607 | if (Sdk.FetchXml.Util.isBoolean(this.uihidden)) {
608 | cNode.setAttribute("uihidden", this.uihidden.toString())
609 | }
610 | if (this.uiname) {
611 | cNode.setAttribute("uiname", this.uiname)
612 | }
613 | if (this.uitype) {
614 | cNode.setAttribute("uitype", this.uitype)
615 | }
616 | /*
617 | Note from fetch.xsd:
618 | The attribute "value" is used for all operators that compare to a single value (for example, eq).
619 | The element "value" is used for operators that compare to multiple values (for example, in).
620 | Some operators require neither the attribute "value" or the element "value" (for example, null).
621 |
622 | Groupings below are guesses and not confirmed.
623 | */
624 | switch (this.operator) {
625 | //Operators used for single values
626 | case "begins-with":
627 | case "ends-with":
628 | case "eq":
629 | case "ge":
630 | case "gt":
631 | case "last-x-days":
632 | case "last-x-fiscal-periods":
633 | case "last-x-fiscal-years":
634 | case "last-x-hours":
635 | case "last-x-months":
636 | case "last-x-weeks":
637 | case "last-x-years":
638 | case "last-year":
639 | case "le":
640 | case "like":
641 | case "lt":
642 | case "ne":
643 | case "neq": //Is this the same as 'ne'?
644 | case "next-x-days":
645 | case "next-x-fiscal-periods":
646 | case "next-x-fiscal-years":
647 | case "next-x-hours":
648 | case "next-x-months":
649 | case "next-x-weeks":
650 | case "next-x-years":
651 | case "not-begin-with":
652 | case "not-end-with":
653 | case "not-like":
654 | case "olderthan-x-days":
655 | case "olderthan-x-hours":
656 | case "olderthan-x-minutes":
657 | case "olderthan-x-months":
658 | case "olderthan-x-weeks":
659 | case "olderthan-x-years":
660 | case "on":
661 | case "on-or-after":
662 | case "on-or-before":
663 | case "in-fiscal-period":
664 | case "in-fiscal-year":
665 |
666 | if (this.values.length == 1) {
667 | cNode.setAttribute("value", this.values[0].value)
668 | }
669 | else {
670 | var enumPropertyName = Sdk.FetchXml.Util.getEnumNameFromValue(Sdk.FetchXml.Operator, this.operator);
671 | throw new Error("Sdk.FetchXml.condition values property must contain single value when the Sdk.FetchXml.Operator." + enumPropertyName + " operator is used.");
672 | }
673 | break;
674 | //Operators used for multiple values
675 | case "between":
676 | case "in":
677 | case "not-between":
678 | case "not-in":
679 | case "in-fiscal-period-and-year":
680 | case "in-or-after-fiscal-period-and-year":
681 | case "in-or-before-fiscal-period-and-year":
682 | if (this.values.length > 1) {
683 | this.values.forEach(function (v) {
684 | cNode.appendChild(v.toXml(doc));
685 | })
686 | }
687 | else {
688 | var enumPropertyName = Sdk.FetchXml.Util.getEnumNameFromValue(Sdk.FetchXml.Operator, this.operator);
689 | throw new Error("Sdk.FetchXml.condition values property must contain multiple values when the Sdk.FetchXml.Operator." + enumPropertyName + " operator is used.");
690 | }
691 | break;
692 | //Operators that require no values
693 | case "above":
694 | case "eq-businessid":
695 | case "eq-or-above":
696 | case "eq-or-under":
697 | case "eq-userid": //?
698 | case "eq-userlanguage": //?
699 | case "eq-useroruserhierarchy":
700 | case "eq-useroruserhierarchyandteams":
701 | case "eq-useroruserteams":
702 | case "eq-userteams":
703 | case "last-fiscal-period":
704 | case "last-fiscal-year":
705 | case "last-month":
706 | case "last-seven-days":
707 | case "last-week":
708 | case "ne-businessid"://?
709 | case "ne-userid"://?
710 | case "next-fiscal-period":
711 | case "next-fiscal-year":
712 | case "next-month":
713 | case "next-seven-days":
714 | case "next-week":
715 | case "next-year":
716 | case "not-null":
717 | case "not-under":
718 | case "null":
719 | case "this-fiscal-period":
720 | case "this-fiscal-year":
721 | case "this-month":
722 | case "this-week":
723 | case "this-year":
724 | case "today":
725 | case "tomorrow":
726 | case "under":
727 | case "yesterday":
728 | //No value required
729 | if (this.values.length > 0) {
730 | var enumPropertyName = Sdk.FetchXml.Util.getEnumNameFromValue(Sdk.FetchXml.Operator, this.operator);
731 | console.log("Sdk.FetchXml.condition doesn't require values when the Sdk.FetchXml.Operator.%s operator is used. The values passed were ignored.", enumPropertyName);
732 | }
733 |
734 | break;
735 | default:
736 | throw new Error(this.operator + " is an unexpected Sdk.FetchXml.Operator value.")
737 | break;
738 | }
739 |
740 |
741 | return cNode;
742 | }
743 | //Internal use only
744 | static conditionFromXml(xml) {
745 | var attributeName = xml.attributes.getNamedItem("attribute").nodeValue;
746 | var operator = xml.attributes.getNamedItem("operator").nodeValue;
747 |
748 | var conditionObj = new Sdk.FetchXml.condition(attributeName, operator);
749 |
750 | Sdk.FetchXml.Util.parseAttributes(xml, conditionObj, (conditionObj, name, value) => {
751 | switch (name) {
752 | case "column":
753 | case "entityname":
754 | case "aggregate":
755 | case "alias":
756 | case "uiname":
757 | case "uitype":
758 | conditionObj[name] = value;
759 | break;
760 | case "rowaggregate":
761 | conditionObj.rowAggregate = value;
762 | break;
763 | case "uihidden":
764 | conditionObj.uihidden = Util.convertFetchBoolType(value);
765 | break;
766 | case "value":
767 | conditionObj.addValue(value);
768 | break;
769 | default:
770 | break;
771 | }
772 | })
773 |
774 | for (var i = 0; i < xml.childNodes.length; i++) {
775 |
776 | if (xml.childNodes[i].nodeName == "value") {
777 | conditionObj.addValue(value.valueFromXml(xml.childNodes[i]));
778 | }
779 |
780 | }
781 | return conditionObj;
782 | }
783 |
784 | }
785 | @sealed
786 | export class entity {
787 | /**
788 | * Contains the data for a fetchXml entity element.
789 | * @param name The logical name of the attribute
790 | * @param [attributes] The attributes to include with the entity
791 | * @param [orders] The orders to apply to the query
792 | * @param [filters] The filters to apply to the query
793 | */
794 | constructor(name: string, attributes?: Array, orders?: Array, filters?: Array) {
795 | if (!(this instanceof Sdk.FetchXml.entity))
796 | { return new Sdk.FetchXml.entity(name, attributes, orders, filters) }
797 |
798 | this.name = name;
799 | if (attributes)
800 | this.attributes = attributes;
801 | if (orders)
802 | this.orders = orders;
803 | if (filters)
804 | this.filters = filters;
805 | }
806 |
807 | private _allAttributes: boolean = null;
808 | private _attributes: Array = [];
809 | private _orders: Array = [];
810 | private _linkEntities: Array = [];
811 | private _filters: Array = [];
812 | private _name: string;
813 |
814 | /**
815 | * Gets or sets whether all attributes for the entity should be returned
816 | */
817 | public get allAttributes(): boolean {
818 | return this._allAttributes;
819 | }
820 | public set allAttributes(value: boolean) {
821 | if (!Sdk.FetchXml.Util.isBooleanOrNull(value)) {
822 | throw new Error("Sdk.FetchXml.entity.allAttributes must be a boolean value or null.")
823 | }
824 | this._allAttributes = value;
825 | }
826 | /**
827 | * Gets or sets the array of attribute of the entity to be returned in the query results
828 | */
829 | public get attributes(): Array {
830 | return this._attributes;
831 | }
832 | public set attributes(value: Array) {
833 | if (!Sdk.FetchXml.Util.isAttributeArrayOrNull(value)) {
834 | throw new Error("Sdk.FetchXml.entity.attributes must be an array of Sdk.FetchXml.attribute or null.")
835 | }
836 | if (value == null) {
837 | this._attributes = [];
838 | } else {
839 | this._attributes = value;
840 | }
841 |
842 | }
843 | /**
844 | * Gets or sets the array of attribute of the entity to be returned in the query results
845 | */
846 | public get orders(): Array {
847 | return this._orders;
848 | }
849 | public set orders(value: Array) {
850 | if (!Sdk.FetchXml.Util.isOrderArrayOrNull(value)) {
851 | throw new Error("Sdk.FetchXml.entity.orders must be an array of Sdk.FetchXml.order or null.")
852 | }
853 | if (value == null) {
854 | this._orders = [];
855 | } else {
856 | this._orders = value;
857 | }
858 |
859 | }
860 | /**
861 | * Gets or sets the array of related entities to be returned in the query results
862 | */
863 | public get linkEntities(): Array {
864 | return this._linkEntities;
865 | }
866 | public set linkEntities(value: Array) {
867 | if (!Sdk.FetchXml.Util.isLinkEntityArrayOrNull(value)) {
868 | throw new Error("Sdk.FetchXml.entity.linkEntities must be an array of Sdk.FetchXml.linkEntity or null.")
869 | }
870 | if (value == null) {
871 | this._linkEntities = [];
872 | } else {
873 | this._linkEntities = value;
874 | }
875 |
876 | }
877 | /**
878 | * Gets or sets the array of filters to be applied to the query results
879 | */
880 | public get filters(): Array {
881 | return this._filters;
882 | }
883 | public set filters(value: Array) {
884 | if (!Sdk.FetchXml.Util.isFilterArrayOrNull(value)) {
885 | throw new Error("Sdk.FetchXml.entity.filters must be an array of Sdk.FetchXml.filter or null.")
886 | }
887 | if (value == null) {
888 | this._filters = [];
889 | } else {
890 | this._filters = value;
891 | }
892 |
893 | }
894 | /**
895 | * Gets or sets the logical name of the entity
896 | */
897 | public get name(): string {
898 | return this._name;
899 | }
900 | public set name(value: string) {
901 | if (!Sdk.FetchXml.Util.isString(value)) {
902 | throw new Error("Sdk.FetchXml.entity.name must be a string.")
903 | }
904 | this._name = value;
905 |
906 | }
907 |
908 | /** @description Adds an attribute to the attribute collection
909 | * @param {Sdk.FetchXml.attribute | string} attributeOrAttributeName the attribute or attribute name to add
910 | * @returns {Sdk.FetchXml.entity}
911 | */
912 | public addAttribute(attributeOrAttributeName: Sdk.FetchXml.attribute | string) {
913 | if (Sdk.FetchXml.Util.isString(attributeOrAttributeName)) {
914 |
915 | // Some saved queries have duplicate attributes defined, so this is a bit more strict than it has to be.
916 | var exists = false;
917 | this.attributes.forEach(function (a) {
918 | if (a.name == attributeOrAttributeName) {
919 | exists = true;
920 | }
921 | });
922 | if (!exists) {
923 | this.attributes.push(new Sdk.FetchXml.attribute(attributeOrAttributeName))
924 | }
925 | return this;
926 | }
927 | if (Sdk.FetchXml.Util.isAttribute(attributeOrAttributeName)) {
928 | var exists = false;
929 | this.attributes.forEach(function (a) {
930 | if (a.name == (attributeOrAttributeName).name) {
931 | exists = true;
932 | }
933 | });
934 | if (!exists) {
935 | this.attributes.push(attributeOrAttributeName);
936 | }
937 | }
938 | else {
939 | throw new Error("Sdk.FetchXml.entity addAttribute method attributeOrAttributeName parameter must be an Sdk.FetchXml.attribute or a string value.");
940 | }
941 | return this;
942 | }
943 |
944 | /** @description Removes an attribute from the attributes collection by name
945 | * @param {string} attributeName The name of the attribute to remove
946 | * @returns {Sdk.FetchXml.entity}
947 | */
948 | public removeAttributeByName(attributeName: string) {
949 | Sdk.FetchXml.Util.removeCollectionValueByProperty(this.attributes, "name", attributeName)
950 | }
951 |
952 | /** @description Removes an attribute from the attributes collection by reference
953 | * @param {Sdk.FetchXml.attribute} attribute The attribute to remove
954 | * @returns {Sdk.FetchXml.entity}
955 | */
956 | public removeAttributeByRef(attribute: Sdk.FetchXml.attribute) {
957 | Sdk.FetchXml.Util.removeCollectionValueByRef(this.attributes, attribute);
958 | }
959 |
960 | /** @description Removes an attribute from the attributes collection
961 | * @param {Sdk.FetchXml.attribute} attribute The attribute to remove
962 | * @returns {Sdk.FetchXml.entity}
963 | */
964 | public removeAttribute(attribute: Sdk.FetchXml.attribute) {
965 | Sdk.FetchXml.Util.removeCollectionValue(this.attributes, attribute);
966 | }
967 |
968 | /** @description Adds an order to the orders collection
969 | * @param {Sdk.FetchXml.order | string} orderOrAttribute The order to add to the attributes collection or the Attribute property of a new order to create
970 | * @param {boolean} descending Whether the order is descending. True if descending, otherwise false
971 | * @param {string} alias The alias to set for the order
972 | * @returns {Sdk.FetchXml.entity}
973 | */
974 | public addOrder(orderOrAttribute: any, descending?, alias?) {
975 | if (Sdk.FetchXml.Util.isOrder(orderOrAttribute)) {
976 | this.orders.push(orderOrAttribute);
977 | return this;
978 | }
979 | if (Sdk.FetchXml.Util.isString(orderOrAttribute)) {
980 | this.orders.push(new Sdk.FetchXml.order(orderOrAttribute, descending, alias));
981 | }
982 | else {
983 | throw new Error("Sdk.FetchXml.entity addOrder method orderOrAttribute parameter must be a Sdk.FetchXml.order value or a string.");
984 | }
985 | return this;
986 | }
987 |
988 | /** @description Removes a order from the orders collection by reference
989 | * @param {Sdk.FetchXml.order} order The order to remove from the orders collection
990 | * @returns {Sdk.FetchXml.entity}
991 | */
992 | public removeOrderByRef(order: Sdk.FetchXml.order) {
993 | if (!Sdk.FetchXml.Util.isOrder(order)) {
994 | throw new Error("Sdk.FetchXml.entity removeOrderByRef method order parameter must be an Sdk.FetchXml.order.")
995 | }
996 | Sdk.FetchXml.Util.removeCollectionValueByRef(this.orders, order);
997 | return this;
998 | }
999 |
1000 | /** @description Removes a order from the orders collection by value
1001 | * @param {Sdk.FetchXml.order} order The order to remove from the orders collection
1002 | * @returns {Sdk.FetchXml.entity}
1003 | */
1004 | public removeOrder(order) {
1005 | if (!Sdk.FetchXml.Util.isOrder(order)) {
1006 | throw new Error("Sdk.FetchXml.entity removeOrder method order parameter must be an Sdk.FetchXml.order.")
1007 | }
1008 | Sdk.FetchXml.Util.removeCollectionValue(this.orders, order);
1009 | return this;
1010 | }
1011 |
1012 | /** @description Sets the name property of the entity element
1013 | * @param {string} name The name value to apply to the entity
1014 | * @returns {Sdk.FetchXml.entity}
1015 | */
1016 | public setName(name: string) {
1017 | this.name = name;
1018 | return this;
1019 | }
1020 |
1021 | /** @description Sets the allAttributes property of the entity
1022 | * @param {boolean} [allAttributes] The allAttributes value to apply to the entity. The default is true;
1023 | * @returns {Sdk.FetchXml.entity}
1024 | */
1025 | public setAllAttributes(allAttributes?: boolean) {
1026 | if (Sdk.FetchXml.Util.isBoolean(allAttributes)) {
1027 | this.allAttributes = allAttributes;
1028 | }
1029 | else {
1030 | if (Sdk.FetchXml.Util.isNullOrUndefined(allAttributes)) {
1031 | this.allAttributes = true;
1032 | }
1033 | else {
1034 | throw new Error("Sdk.FetchXml.entity setAllAttributes method allAttributes parameter must be a boolean value or null.");
1035 | }
1036 | }
1037 |
1038 | return this;
1039 | }
1040 |
1041 | /** @description Adds an linkEntity to the linkEntities collection
1042 | * @param {Sdk.FetchXml.linkEntity} linkEntity The linkEntity to add to the entity
1043 | * @returns {Sdk.FetchXml.entity}
1044 | */
1045 | public addLinkEntity(linkEntity: Sdk.FetchXml.linkEntity) {
1046 | if (Sdk.FetchXml.Util.isLinkEntity(linkEntity)) {
1047 | this.linkEntities.push(linkEntity);
1048 | return this;
1049 | }
1050 | else {
1051 | throw new Error("Sdk.FetchXml.entity addLinkEntity method linkEntity parameter must be a Sdk.FetchXml.linkEntity value.");
1052 | }
1053 | return this;
1054 | }
1055 |
1056 | /** @description Removes a linkEntity from the linkEntities collection by reference
1057 | * @param {Sdk.FetchXml.linkEntity} linkEntity The linkEntity to remove from the linkEntities collection
1058 | * @returns {Sdk.FetchXml.entity}
1059 | */
1060 | public removeLinkEntityByRef(linkEntity: Sdk.FetchXml.linkEntity) {
1061 | if (!Sdk.FetchXml.Util.isLinkEntity(linkEntity)) {
1062 | throw new Error("Sdk.FetchXml.entity removeLinkEntityByRef method linkEntity parameter must be an Sdk.FetchXml.linkEntity.")
1063 | }
1064 | Sdk.FetchXml.Util.removeCollectionValueByRef(this.linkEntities, linkEntity);
1065 | return this;
1066 | }
1067 |
1068 | /** @description Removes a linkEntity from the linkEntities collection by value
1069 | * @param {Sdk.FetchXml.linkEntity} linkEntity The linkEntity to remove from the linkEntities collection
1070 | * @returns {Sdk.FetchXml.entity}
1071 | */
1072 | public removeLinkEntity(linkEntity: Sdk.FetchXml.linkEntity) {
1073 | if (!Sdk.FetchXml.Util.isLinkEntity(linkEntity)) {
1074 | throw new Error("Sdk.FetchXml.entity removeLinkEntity method linkEntity parameter must be an Sdk.FetchXml.linkEntity.")
1075 | }
1076 | Sdk.FetchXml.Util.removeCollectionValue(this.linkEntities, linkEntity);
1077 | return this;
1078 | }
1079 |
1080 | /** @description Adds an filter to the filters collection
1081 | * @param {Sdk.FetchXml.filter} filter The filter to add to the entity
1082 | * @returns {Sdk.FetchXml.entity}
1083 | */
1084 | public addFilter(filter: Sdk.FetchXml.filter) {
1085 | if (Sdk.FetchXml.Util.isFilter(filter)) {
1086 | this.filters.push(filter);
1087 | return this;
1088 | }
1089 | else {
1090 | throw new Error("Sdk.FetchXml.entity addFilter method filter parameter must be a Sdk.FetchXml.filter value.");
1091 | }
1092 | return this;
1093 | }
1094 |
1095 | /** @description Removes a filter from the filters collection by reference
1096 | * @param {Sdk.FetchXml.filter} filter The filter to remove from the filters collection
1097 | * @returns {Sdk.FetchXml.entity}
1098 | */
1099 | public removeFilterByRef(filter: Sdk.FetchXml.filter) {
1100 | if (!Sdk.FetchXml.Util.isFilter(filter)) {
1101 | throw new Error("Sdk.FetchXml.entity removeFilterByRef method filter parameter must be an Sdk.FetchXml.filter.")
1102 | }
1103 | Sdk.FetchXml.Util.removeCollectionValueByRef(this.filters, filter);
1104 | return this;
1105 | }
1106 |
1107 | /** @description Removes a filter from the filters collection by value
1108 | * @param {Sdk.FetchXml.filter} filter The filter to remove from the filters collection
1109 | * @returns {Sdk.FetchXml.entity}
1110 | */
1111 | public removeFilter(filter: Sdk.FetchXml.filter) {
1112 | if (!Sdk.FetchXml.Util.isFilter(filter)) {
1113 | throw new Error("Sdk.FetchXml.entity removeFilter method filter parameter must be an Sdk.FetchXml.filter.")
1114 | }
1115 | Sdk.FetchXml.Util.removeCollectionValue(this.filters, filter);
1116 | return this;
1117 | }
1118 |
1119 | //internal use only
1120 | toXml(doc: XMLDocument): Node {
1121 | var entityNode = doc.createElement("entity");
1122 | if (this.allAttributes) {
1123 | entityNode.appendChild(doc.createElement("all-attributes"));
1124 | }
1125 | else {
1126 | this.attributes.forEach(function (a, i) {
1127 | entityNode.appendChild(a.toXml(doc));
1128 | })
1129 | }
1130 | this.orders.forEach(function (o, i) {
1131 | entityNode.appendChild(o.toXml(doc));
1132 | })
1133 |
1134 | this.linkEntities.forEach(function (l, i) {
1135 | entityNode.appendChild(l.toXml(doc));
1136 | })
1137 |
1138 | this.filters.forEach(function (f, i) {
1139 | entityNode.appendChild(f.toXml(doc));
1140 | })
1141 |
1142 | //Is required so no need to check
1143 | entityNode.setAttribute("name", this.name);
1144 |
1145 | return entityNode;
1146 | }
1147 | //Internal use only
1148 | static entityFromXml(xml) {
1149 | var entityObj = new Sdk.FetchXml.entity(xml.attributes.getNamedItem("name").nodeValue);
1150 | entityObj.allAttributes = (xml.getElementsByTagName("all-attributes").length == 1);
1151 |
1152 | for (var i = 0; i < xml.childNodes.length; i++) {
1153 |
1154 | if (xml.childNodes[i].nodeName == "attribute") {
1155 | entityObj.addAttribute(attribute.attributeFromXml(xml.childNodes[i]));
1156 | }
1157 | if (xml.childNodes[i].nodeName == "order") {
1158 |
1159 | entityObj.addOrder(order.orderFromXml(xml.childNodes[i]));
1160 | }
1161 | if (xml.childNodes[i].nodeName == "link-entity") {
1162 | entityObj.addLinkEntity(linkEntity.linkEntityFromXml(xml.childNodes[i]));
1163 | }
1164 | if (xml.childNodes[i].nodeName == "filter") {
1165 | entityObj.addFilter(filter.filterFromXml(xml.childNodes[i]));
1166 | }
1167 |
1168 | }
1169 |
1170 | return entityObj;
1171 | }
1172 |
1173 |
1174 | }
1175 | @sealed
1176 | export class fetch {
1177 |
1178 |
1179 | /**
1180 | * Contains the data for a fetchXml fetch element.
1181 | * @param entity The entity that is being queried
1182 | */
1183 | constructor(entity?: Sdk.FetchXml.entity) {
1184 | //new keyword not required
1185 | if (!(this instanceof Sdk.FetchXml.fetch))
1186 | { return new Sdk.FetchXml.fetch(entity) }
1187 | if (entity)
1188 | this.entity = entity;
1189 | }
1190 |
1191 | private _aggregate: boolean = null;
1192 | private _count: number = null;
1193 | private _distinct: boolean = null;
1194 | private _entity: Sdk.FetchXml.entity;
1195 | private _mapping: Sdk.FetchXml.Mapping = null;
1196 | private _minActiveRowVersion: boolean = null;
1197 | private _noLock: boolean = null;
1198 | private _order: Sdk.FetchXml.order = null;
1199 | private _outputFormat: Sdk.FetchXml.OutputFormat = null;
1200 | private _page: number = null;
1201 | private _pagingCookie: string = null;
1202 | private _returnTotalRecordCount: boolean = null;
1203 | private _top: number = null;
1204 | private _utcOffset: number = null;
1205 | private _version: string = null;
1206 |
1207 | /**
1208 | * Gets or sets the aggregate attribute of the fetch element.
1209 | */
1210 | public get aggregate(): boolean {
1211 | return this._aggregate;
1212 | }
1213 | public set aggregate(value: boolean) {
1214 | if (!Sdk.FetchXml.Util.isBooleanOrNull(value)) {
1215 | throw new Error("Sdk.FetchXml.fetch.aggregate must be a boolean value or null.")
1216 | }
1217 | this._aggregate = value;
1218 | }
1219 | /**
1220 | * Gets or sets the count attribute of the fetch element.
1221 | */
1222 | public get count(): number {
1223 | return this._count;
1224 | }
1225 | public set count(value: number) {
1226 | if (!Sdk.FetchXml.Util.isNumberOrNull(value)) {
1227 | throw new Error("Sdk.FetchXml.fetch.count must be a number value or null.")
1228 | }
1229 | this._count = value;
1230 | }
1231 | /**
1232 | * Gets or sets the distinct attribute of the fetch element.
1233 | */
1234 | public get distinct(): boolean {
1235 | return this._distinct;
1236 | }
1237 | public set distinct(value: boolean) {
1238 | if (!Sdk.FetchXml.Util.isBooleanOrNull(value)) {
1239 | throw new Error("Sdk.FetchXml.fetch.distinct must be a boolean value or null.")
1240 | }
1241 | this._distinct = value;
1242 | }
1243 | /**
1244 | * Gets or sets the entity attribute of the fetch element.
1245 | */
1246 | public get entity(): Sdk.FetchXml.entity {
1247 | return this._entity;
1248 | }
1249 | public set entity(value: Sdk.FetchXml.entity) {
1250 | if (!Sdk.FetchXml.Util.isEntity(value)) {
1251 | throw new Error("Sdk.FetchXml.fetch.entity must be a Sdk.FetchXml.entity value.")
1252 | }
1253 | this._entity = value;
1254 | }
1255 | /**
1256 | * Gets or sets the mapping attribute of the fetch element.
1257 | */
1258 | public get mapping(): Sdk.FetchXml.Mapping {
1259 | return this._mapping;
1260 | }
1261 | public set mapping(value: Sdk.FetchXml.Mapping) {
1262 | if (!Sdk.FetchXml.Util.isEnumMemberOrNull(Sdk.FetchXml.Mapping, value)) {
1263 | throw new Error("Sdk.FetchXml.fetch.mapping must be a Sdk.FetchXml.Mapping value or null.")
1264 | }
1265 | this._mapping = value;
1266 | }
1267 | /**
1268 | * Gets or sets the minActiveRowVersion attribute of the fetch element.
1269 | */
1270 | public get minActiveRowVersion(): boolean {
1271 | return this._minActiveRowVersion;
1272 | }
1273 | public set minActiveRowVersion(value: boolean) {
1274 | if (!Sdk.FetchXml.Util.isBooleanOrNull(value)) {
1275 | throw new Error("Sdk.FetchXml.fetch.minActiveRowVersion must be a boolean value or null.")
1276 | }
1277 | this._minActiveRowVersion = value;
1278 | }
1279 | /**
1280 | * Gets or sets the noLock attribute of the fetch element.
1281 | */
1282 | public get noLock(): boolean {
1283 | return this._noLock;
1284 | }
1285 | public set noLock(value: boolean) {
1286 | if (!Sdk.FetchXml.Util.isBooleanOrNull(value)) {
1287 | throw new Error("Sdk.FetchXml.fetch.noLock must be a boolean value or null.")
1288 | }
1289 | this._noLock = value;
1290 | }
1291 | /**
1292 | * Gets or sets the order attribute of the fetch element.
1293 | */
1294 | public get order(): Sdk.FetchXml.order {
1295 | return this._order;
1296 | }
1297 | public set order(value: Sdk.FetchXml.order) {
1298 | if (!Sdk.FetchXml.Util.isOrderOrNull(value)) {
1299 | throw new Error("Sdk.FetchXml.fetch.order must be a Sdk.FetchXml.order value or null.")
1300 | }
1301 | this._order = value;
1302 | }
1303 | /**
1304 | * Gets or sets the outputFormat attribute of the fetch element.
1305 | */
1306 | public get outputFormat(): Sdk.FetchXml.OutputFormat {
1307 | return this._outputFormat;
1308 | }
1309 | public set outputFormat(value: Sdk.FetchXml.OutputFormat) {
1310 | if (!Sdk.FetchXml.Util.isEnumMemberOrNull(Sdk.FetchXml.OutputFormat, value)) {
1311 | throw new Error("Sdk.FetchXml.fetch.outputFormat must be a Sdk.FetchXml.OutputFormat value or null.")
1312 | }
1313 | this._outputFormat = value;
1314 | }
1315 | /**
1316 | * Gets or sets the page attribute of the fetch element.
1317 | */
1318 | public get page(): number {
1319 | return this._page;
1320 | }
1321 | public set page(value: number) {
1322 | if (!Sdk.FetchXml.Util.isNumberOrNull(value)) {
1323 | throw new Error("Sdk.FetchXml.fetch.page must be a number value or null.")
1324 | }
1325 | this._page = value;
1326 | }
1327 | /**
1328 | * Gets or sets the pagingCookie attribute of the fetch element.
1329 | */
1330 | public get pagingCookie(): string {
1331 | return this._pagingCookie;
1332 | }
1333 | public set pagingCookie(value: string) {
1334 | if (!Sdk.FetchXml.Util.isStringOrNull(value)) {
1335 | throw new Error("Sdk.FetchXml.fetch.pagingCookie must be a string value or null.")
1336 | }
1337 | this._pagingCookie = value;
1338 | }
1339 | /**
1340 | * Gets or sets the returnTotalRecordCount attribute of the fetch element.
1341 | */
1342 | public get returnTotalRecordCount(): boolean {
1343 | return this._returnTotalRecordCount;
1344 | }
1345 | public set returnTotalRecordCount(value: boolean) {
1346 | if (!Sdk.FetchXml.Util.isBooleanOrNull(value)) {
1347 | throw new Error("Sdk.FetchXml.fetch.returnTotalRecordCount must be a boolean value or null.")
1348 | }
1349 | this._returnTotalRecordCount = value;
1350 | }
1351 | /**
1352 | * Gets or sets the top attribute of the fetch element.
1353 | */
1354 | public get top(): number {
1355 | return this._top;
1356 | }
1357 | public set top(value: number) {
1358 | if (!Sdk.FetchXml.Util.isNumberOrNull(value)) {
1359 | throw new Error("Sdk.FetchXml.fetch.top must be a number value or null.")
1360 | }
1361 | this._top = value;
1362 | }
1363 | /**
1364 | * Gets or sets the utcOffset attribute of the fetch element.
1365 | */
1366 | public get utcOffset(): number {
1367 | return this._utcOffset;
1368 | }
1369 | public set utcOffset(value: number) {
1370 | if (!Sdk.FetchXml.Util.isNumberOrNull(value)) {
1371 | throw new Error("Sdk.FetchXml.fetch.utcOffset must be a number value or null.")
1372 | }
1373 | this._utcOffset = value;
1374 | }
1375 | /**
1376 | * Gets or sets the version attribute of the fetch element.
1377 | */
1378 | public get version(): string {
1379 | return this._version;
1380 | }
1381 | public set version(value: string) {
1382 | if (!Sdk.FetchXml.Util.isStringOrNull(value)) {
1383 | throw new Error("Sdk.FetchXml.fetch.version must be a string value or null.")
1384 | }
1385 | this._version = value;
1386 | }
1387 |
1388 | /** @description Sets the aggregate attribute of the fetch element
1389 | * @param {boolean | null} aggregate The aggregate value to apply to the fetch element
1390 | * @returns {Sdk.FetchXml.fetch}
1391 | */
1392 | public setAggregate(aggregate?: boolean) {
1393 | (aggregate) ? this.aggregate = aggregate : this.aggregate = null;
1394 | return this;
1395 | }
1396 |
1397 | /** @description Sets the count attribute of the fetch element
1398 | * @param {number | null} count The count value to apply to the fetch element
1399 | * @returns {Sdk.FetchXml.fetch}
1400 | */
1401 | public setCount(count?: number) {
1402 | (count) ? this.count = count : this.count = null;
1403 | return this;
1404 | }
1405 |
1406 | /** @description Sets the distinct attribute of the fetch element
1407 | * @param {boolean | null} distinct The distinct value to apply to the fetch element
1408 | * @returns {Sdk.FetchXml.fetch}
1409 | */
1410 | public setDistinct(distinct?: boolean) {
1411 | (distinct) ? this.distinct = distinct : this.distinct = null;
1412 | return this;
1413 | }
1414 |
1415 | /** @description Sets the aggregate entity of the fetch element
1416 | * @param {Sdk.FetchXml.entity} entity The entity value to apply to the fetch element
1417 | * @returns {Sdk.FetchXml.fetch}
1418 | */
1419 | public setEntity(entity: Sdk.FetchXml.entity) {
1420 | this.entity = entity;
1421 | return this;
1422 | }
1423 |
1424 | /** @description Sets the mapping attribute of the fetch element
1425 | * @param {Sdk.FetchXml.Mapping} mapping The mapping value to apply to the fetch element
1426 | * @returns {Sdk.FetchXml.fetch}
1427 | */
1428 | public setMapping(mapping?: Sdk.FetchXml.Mapping) {
1429 | (mapping) ? this.mapping = mapping : this.mapping = null;
1430 | return this;
1431 | }
1432 |
1433 | /** @description Sets the minActiveRowVersion attribute of the fetch element
1434 | * @param {boolean | null} minActiveRowVersion The minActiveRowVersion value to apply to the fetch element
1435 | * @returns {Sdk.FetchXml.fetch}
1436 | */
1437 | public setMinActiveRowVersion(minActiveRowVersion?: boolean) {
1438 | (minActiveRowVersion) ? this.minActiveRowVersion = minActiveRowVersion : this.minActiveRowVersion = null;
1439 | return this;
1440 | }
1441 |
1442 | /** @description Sets the noLock attribute of the fetch element
1443 | * @param {boolean | null} noLock The noLock value to apply to the fetch element
1444 | * @returns {Sdk.FetchXml.fetch}
1445 | */
1446 | public setNoLock(noLock: boolean = null) {
1447 | this.noLock = noLock;
1448 | return this;
1449 | }
1450 |
1451 | /** @description Sets the order attribute of the fetch element
1452 | * @param {Sdk.FetchXml.order | null} order The order value to apply to the fetch element
1453 | * @returns {Sdk.FetchXml.fetch}
1454 | */
1455 | public setOrder(order: Sdk.FetchXml.order = null) {
1456 | this.order = order;
1457 | return this;
1458 | }
1459 |
1460 | /** @description Sets the outputFormat attribute of the fetch element
1461 | * @param {Sdk.FetchXml.OutputFormat | null} outputFormat The outputFormat value to apply to the fetch element
1462 | * @returns {Sdk.FetchXml.fetch}
1463 | */
1464 | public setOutputFormat(outputFormat?: Sdk.FetchXml.OutputFormat) {
1465 | (outputFormat) ? this.outputFormat = outputFormat : this.outputFormat = null;
1466 | return this;
1467 | }
1468 |
1469 | /** @description Sets the page attribute of the fetch element
1470 | * @param {number | null} page The page value to apply to the fetch element
1471 | * @returns {Sdk.FetchXml.fetch}
1472 | */
1473 | public setPage(page?: number) {
1474 | (page) ? this.page = page : this.page = null;
1475 | return this;
1476 | }
1477 |
1478 | /** @description Sets the pagingCookie attribute of the fetch element
1479 | * @param {string | null} pagingCookie The pagingCookie value to apply to the fetch element
1480 | * @returns {Sdk.FetchXml.fetch}
1481 | */
1482 | public setPagingCookie(pagingCookie: string = null) {
1483 | this.pagingCookie = pagingCookie;
1484 | return this;
1485 | }
1486 |
1487 | /** @description Sets the returnTotalRecordCount attribute of the fetch element
1488 | * @param {boolean} returnTotalRecordCount The returnTotalRecordCount value to apply to the fetch element
1489 | * @returns {Sdk.FetchXml.fetch}
1490 | */
1491 | public setReturnTotalRecordCount(returnTotalRecordCount?: boolean) {
1492 | (returnTotalRecordCount) ? this.returnTotalRecordCount = returnTotalRecordCount : this.returnTotalRecordCount = null;
1493 | return this;
1494 | }
1495 |
1496 | /** @description Sets the top attribute of the fetch element
1497 | * @param {number | null} top The top value to apply to the fetch element
1498 | * @returns {Sdk.FetchXml.fetch}
1499 | */
1500 | public setTop(top?: number) {
1501 | (top) ? this.top = top : this.top = null;
1502 | return this;
1503 | }
1504 |
1505 | /** @description Sets the utcOffset attribute of the fetch element
1506 | * @param {number | null} utcOffset The utcOffset value to apply to the fetch element
1507 | * @returns {Sdk.FetchXml.fetch}
1508 | */
1509 | public setUtcOffset(utcOffset?: number) {
1510 | (utcOffset) ? this.utcOffset = utcOffset : this.utcOffset = null;
1511 | return this;
1512 | }
1513 |
1514 | /** @description Sets the version attribute of the fetch element
1515 | * @param {string | null} version The version value to apply to the fetch element
1516 | * @returns {Sdk.FetchXml.fetch}
1517 | */
1518 | public setVersion(version?: string) {
1519 | (version) ? this.version = version : this.version = null;
1520 | return this;
1521 | }
1522 |
1523 | /**
1524 | * Serializes the fetch query into a FetchXML string
1525 | */
1526 | public toXml(): string {
1527 |
1528 | var root = "";
1529 | var doc = new DOMParser().parseFromString(root, "text/xml");
1530 | if (this.version) {
1531 | doc.documentElement.setAttribute("version", this.version)
1532 | }
1533 | if (this.outputFormat) {
1534 | doc.documentElement.setAttribute("output-format", this.outputFormat)
1535 | }
1536 | if (this.mapping) {
1537 | doc.documentElement.setAttribute("mapping", this.mapping)
1538 | }
1539 | if (this.aggregate) {
1540 | doc.documentElement.setAttribute("aggregate", (this.aggregate) ? "true" : "false")
1541 | }
1542 | if (this.count) {
1543 | doc.documentElement.setAttribute("count", this.count.toString())
1544 | }
1545 | if (this.distinct) {
1546 | doc.documentElement.setAttribute("distinct", (this.distinct) ? "true" : "false")
1547 | }
1548 | if (this.entity) {
1549 | doc.documentElement.appendChild(this.entity.toXml(doc));
1550 | }
1551 |
1552 | if (this.minActiveRowVersion) {
1553 | doc.documentElement.setAttribute("min-active-row-version", (this.minActiveRowVersion) ? "true" : "false")
1554 | }
1555 | if (this.noLock) {
1556 | doc.documentElement.setAttribute("no-lock", (this.noLock) ? "true" : "false")
1557 | }
1558 | if (this.order) {
1559 | doc.documentElement.appendChild(this.order.toXml(doc));
1560 | }
1561 |
1562 | if (this.page) {
1563 | doc.documentElement.setAttribute("page", this.page.toString())
1564 | }
1565 | if (this.pagingCookie) {
1566 | doc.documentElement.setAttribute("paging-cookie", this.pagingCookie) //Does this need special handling?
1567 | }
1568 | if (this.returnTotalRecordCount) {
1569 | doc.documentElement.setAttribute("returntotalrecordcount", (this.returnTotalRecordCount) ? "true" : "false")
1570 | }
1571 | if (this.top) {
1572 | doc.documentElement.setAttribute("top", this.top.toString())
1573 | }
1574 | if (this.utcOffset) {
1575 | doc.documentElement.setAttribute("utc-offset", this.utcOffset.toString())
1576 | }
1577 |
1578 | return new XMLSerializer().serializeToString(doc);
1579 | }
1580 | /**
1581 | * Instantiates a fetch object from a fetchXml string
1582 | * @param xml A FetchXML string
1583 | * @returns Sdk.FetchXml.fetch
1584 | */
1585 | public static fromXml(xml: string) {
1586 | var doc = new DOMParser().parseFromString(xml, "text/xml");
1587 | var fetchObj = new Sdk.FetchXml.fetch();
1588 | var errorMessage = "The XML string is not a valid fetchXML document";
1589 |
1590 | if (doc.documentElement.localName == "fetch") {
1591 |
1592 | Sdk.FetchXml.Util.parseAttributes(doc.documentElement, fetchObj, (fetchObj, name, value) => {
1593 | switch (name) {
1594 | case "count":
1595 | case "top":
1596 | case "page":
1597 | fetchObj[name] = parseInt(value, 10);
1598 | break;
1599 | case "utc-offset":
1600 | if (!isNaN(value)) {
1601 | fetchObj.utcOffset = parseInt(value, 10);
1602 | }
1603 | else {
1604 | fetchObj.utcOffset = null;
1605 | }
1606 | break;
1607 | case "paging-cookie":
1608 | fetchObj.pagingCookie = value;
1609 | break;
1610 | case "min-active-row-version":
1611 | fetchObj.minActiveRowVersion = (value == "true") ? true : false;
1612 | break;
1613 | case "output-format":
1614 | fetchObj.outputFormat = value;
1615 | break;
1616 | case "returntotalrecordcount":
1617 | fetchObj.returnTotalRecordCount = (value == "true") ? true : false;
1618 | break;
1619 | case "no-lock":
1620 | fetchObj.noLock = (value == "true") ? true : false;
1621 | break;
1622 | case "aggregate": //xs:boolean
1623 | case "distinct":
1624 | fetchObj[name] = (value == "true") ? true : false;
1625 | break;
1626 | default:
1627 | fetchObj[name] = value;
1628 | break;
1629 | }
1630 | });
1631 |
1632 | for (var i = 0; i < doc.documentElement.childNodes.length; i++) {
1633 |
1634 | if (doc.documentElement.childNodes[i].nodeName == "entity") {
1635 | fetchObj.entity = Sdk.FetchXml.entity.entityFromXml(doc.documentElement.childNodes[i]);
1636 | }
1637 | if (doc.documentElement.childNodes[i].nodeName == "order") {
1638 | fetchObj.order = Sdk.FetchXml.order.orderFromXml(doc.documentElement.childNodes[i]);
1639 | }
1640 | }
1641 |
1642 | }
1643 | else {
1644 | throw new Error(errorMessage);
1645 | }
1646 |
1647 | return fetchObj;
1648 | }
1649 |
1650 | }
1651 | @sealed
1652 | export class filter {
1653 | /** @description Contains the data for a fetchXml filter element.
1654 | * @param [type] The type of filter: 'and' or 'or'. Default is 'and'
1655 | * @param [conditions] An array of Sdk.FetchXml.condition to apply to the filter
1656 | * @param [filters] An array of Sdk.FetchXml.filter to apply to the filter
1657 | * @property conditions Gets or sets the array of Sdk.FetchXml.condition to apply in the filter
1658 | * @property filters Gets or sets the array of Sdk.FetchXml.filter to apply to the filter
1659 | * @property type Gets or sets the type of filter.
1660 | * @property isQuickFindFields Gets or sets the isQuickFindFields property of the filter
1661 | * @returns {Sdk.FetchXml.filter}
1662 | */
1663 | constructor(type?: string, conditions?: Array, filters?: Array) {
1664 | //new keyword is not required in JS
1665 | if (!(this instanceof filter))
1666 | { return new filter(type, conditions, filters) }
1667 | if (type)
1668 | this.type = type;
1669 | if (conditions)
1670 | this.conditions = conditions;
1671 | if (filters)
1672 | this.filters = filters;
1673 | }
1674 |
1675 | private _conditions: Array = [];
1676 | private _filters: Array = [];
1677 | private _type: FilterType = null;
1678 | private _isQuickFindFields: boolean = null;
1679 |
1680 | /**
1681 | * Gets or sets the array of condition to be applied to the query results
1682 | */
1683 | public get conditions(): Array {
1684 | return this._conditions;
1685 | }
1686 | public set conditions(value: Array) {
1687 | if (!Util.isFilterArrayOrNull(value)) {
1688 | throw new Error("Sdk.FetchXml.filter.conditions must be an array of Sdk.FetchXml.condition or null.")
1689 | }
1690 | if (value == null) {
1691 | this._conditions = [];
1692 | } else {
1693 | this._conditions = value;
1694 | }
1695 | }
1696 | /**
1697 | * Gets or sets the array of filters to be applied to the query results
1698 | */
1699 | public get filters(): Array {
1700 | return this._filters;
1701 | }
1702 | public set filters(value: Array) {
1703 | if (!Util.isFilterArrayOrNull(value)) {
1704 | throw new Error("Sdk.FetchXml.filter.filters must be an array of Sdk.FetchXml.filter or null.")
1705 | }
1706 | if (value == null) {
1707 | this._filters = [];
1708 | } else {
1709 | this._filters = value;
1710 | }
1711 | }
1712 | /**
1713 | * Gets or sets the type property of the filter
1714 | */
1715 | public get type(): FilterType {
1716 | return this._type;
1717 | }
1718 | public set type(value: FilterType) {
1719 | this._type = value;
1720 | }
1721 | /**
1722 | * Gets or sets the isQuickFindFields property of the filter
1723 | */
1724 | public get isQuickFindFields(): boolean {
1725 | return this._isQuickFindFields;
1726 | }
1727 | public set isQuickFindFields(value: boolean) {
1728 | this._isQuickFindFields = value;
1729 | }
1730 |
1731 | /** @description Adds a condition to the conditions collection
1732 | * @param {Sdk.FetchXml.attribute | Sdk.FetchXml.condition} attributeOrCondition When Sdk.FetchXml.condition the condition is added.
1733 | When Sdk.FetchXml.attribute, the attribute property of a new condition
1734 | * @param {Sdk.FetchXml.Operator} [operator] The operator property for a new condition. Required when the first parameter is an Sdk.FetchXml.attribute
1735 | * @param {Array} [values] The values to compare for a new condition.
1736 | * @returns {Sdk.FetchXml.filter}
1737 | */
1738 | public addCondition(attributeOrCondition: any, operator?, values?) {
1739 | if (Util.isCondition(attributeOrCondition)) {
1740 | this.conditions.push(attributeOrCondition);
1741 | }
1742 | else {
1743 | this.conditions.push(new condition(attributeOrCondition, operator, values));
1744 | }
1745 |
1746 | return this;
1747 | }
1748 |
1749 | /** @description Removes a condition from the conditions collection by reference
1750 | * @param {Sdk.FetchXml.condition} condition The condition to remove from the conditions collection
1751 | * @returns {Sdk.FetchXml.filter}
1752 | */
1753 | public removeConditionByRef(condition) {
1754 | if (!Util.isCondition(condition)) {
1755 | throw new Error("Sdk.FetchXml.filter removeConditionByRef method condition parameter must be an Sdk.FetchXml.condition.")
1756 | }
1757 | Util.removeCollectionValueByRef(this.conditions, condition);
1758 |
1759 | return this;
1760 | }
1761 |
1762 | /** @description Removes a condition from the conditions collection by value
1763 | * @param {Sdk.FetchXml.condition} condition The condition to remove from the conditions collection
1764 | * @returns {Sdk.FetchXml.filter}
1765 | */
1766 | public removeCondition(condition) {
1767 | if (!Util.isCondition(condition)) {
1768 | throw new Error("Sdk.FetchXml.filter removeCondition method condition parameter must be an Sdk.FetchXml.condition.")
1769 | }
1770 | Util.removeCollectionValue(this.conditions, condition);
1771 |
1772 | return this;
1773 | }
1774 |
1775 | /** @description Adds a filter to the filters collection
1776 | * @param {Sdk.FetchXml.filter} filter The filter to add to the filters collectio
1777 | * @returns {Sdk.FetchXml.filter}
1778 | */
1779 | public addFilter(filter) {
1780 | if (Util.isFilter(filter)) {
1781 | this.filters.push(filter);
1782 |
1783 | } else {
1784 | throw new Error("Sdk.FetchXml.filter addFilter method filter parameter must be a Sdk.FetchXml.filter value.")
1785 | }
1786 | return this;
1787 | }
1788 |
1789 | /** @description Removes all references to a filter object
1790 | * @param {Sdk.FetchXml.filter} filter The filter to remove from the filters collectio
1791 | * @returns {Sdk.FetchXml.filter}
1792 | */
1793 | public removeFilterByRef(filter) {
1794 | if (!Util.isFilter(filter)) {
1795 | throw new Error("Sdk.FetchXml.filter removeFilterByRef method filter parameter must be an Sdk.FetchXml.filter.")
1796 | }
1797 | Util.removeCollectionValueByRef(this.filters, filter);
1798 |
1799 | return this;
1800 | }
1801 |
1802 | /** @description Removes all matching filters from the filters collection
1803 | * @param {Sdk.FetchXml.filter} filter The filter to remove from the filters collectio
1804 | * @returns {Sdk.FetchXml.filter}
1805 | */
1806 | public removeFilter(filter) {
1807 | if (!Util.isFilter(filter)) {
1808 | throw new Error("Sdk.FetchXml.filter removeFilter method filter parameter must be an Sdk.FetchXml.filter.")
1809 | }
1810 | Util.removeCollectionValue(this.filters, filter);
1811 |
1812 | return this;
1813 | }
1814 |
1815 | /** @description Sets the isQuickFindFields property
1816 | * @param {boolean | null} value The value to set
1817 | * @returns {Sdk.FetchXml.filter}
1818 | */
1819 | public setIsQuickFindFields(value) {
1820 | this.isQuickFindFields = value;
1821 | return this;
1822 | }
1823 |
1824 | /** @description Sets the type property
1825 | * @param {Sdk.FetchXml.FilterType} value The value to set
1826 | * @returns {Sdk.FetchXml.filter}
1827 | */
1828 | public setType(value) {
1829 | this.type = value;
1830 | return this;
1831 | }
1832 |
1833 | //Internal use only
1834 | toXml(doc: XMLDocument): Node {
1835 | var fNode = doc.createElement("filter");
1836 | if (this.type) {
1837 | fNode.setAttribute("type", this.type)
1838 | }
1839 | if (Util.isBoolean(this.isQuickFindFields)) {
1840 | fNode.setAttribute("isquickfindfields", this.isQuickFindFields.toString())
1841 | }
1842 | this.conditions.forEach(function (c) {
1843 | fNode.appendChild(c.toXml(doc));
1844 | })
1845 | this.filters.forEach(function (f) {
1846 | fNode.appendChild(f.toXml(doc));
1847 | })
1848 | return fNode;
1849 | }
1850 |
1851 | static filterFromXml(xml) {
1852 | var filterObj = new filter();
1853 |
1854 | Util.parseAttributes(xml, filterObj, (filterObj, name, value) => {
1855 | switch (name) {
1856 | case "type":
1857 | filterObj.type = value;
1858 | break;
1859 | case "isquickfindfields":
1860 | filterObj.isQuickFindFields = (value == "true" || value == "1") ? true : false;
1861 | break;
1862 | default:
1863 | break;
1864 | }
1865 | });
1866 |
1867 |
1868 |
1869 | for (var i = 0; i < xml.childNodes.length; i++) {
1870 |
1871 | if (xml.childNodes[i].nodeName == "condition") {
1872 | filterObj.addCondition(condition.conditionFromXml(xml.childNodes[i]));
1873 | }
1874 |
1875 | if (xml.childNodes[i].nodeName == "filter") {
1876 | filterObj.addFilter(filter.filterFromXml(xml.childNodes[i]));
1877 | }
1878 |
1879 | }
1880 |
1881 | return filterObj;
1882 | }
1883 |
1884 | }
1885 | @sealed
1886 | export class linkEntity {
1887 | /**
1888 | * Contains the data for a fetchXml link-entity element.
1889 | * @param name The logical name of the entity
1890 | * @param from The from property of the linkEntity
1891 | * @param to The to property of the linkEntity
1892 | * @param linktype The linktype property of the linkEntity
1893 | * @param alias The alias property of the linkEntity
1894 | */
1895 | constructor(name: string, from?: string, to?: string, linktype?: string, alias?: string) {
1896 | if (!(this instanceof linkEntity))
1897 | { return new linkEntity(name, from, to, linktype, alias) }
1898 |
1899 | this.name = name;
1900 | if (from)
1901 | this.from = from;
1902 | if (to)
1903 | this.to = to;
1904 | if (linktype)
1905 | this.linktype = linktype;
1906 | if (alias)
1907 | this.alias = alias;
1908 | }
1909 |
1910 | private _name: string = null;
1911 | private _alias: string = null;
1912 | private _from: string = null;
1913 | private _intersect: boolean = null;
1914 | private _linktype: string = null;
1915 | private _to: string = null;
1916 | private _visible: boolean = null;
1917 | private _allAttributes: boolean = null;
1918 | private _attributes: Array = [];
1919 | private _orders: Array = [];
1920 | private _linkEntities: Array = [];
1921 | private _filters: Array = [];
1922 |
1923 | /**
1924 | * Gets or sets the name property of the linkEntity
1925 | */
1926 | public get name(): string {
1927 | return this._name;
1928 | }
1929 | public set name(value: string) {
1930 | this._name = value;
1931 | }
1932 | /**
1933 | * Gets or sets the alias property of the linkEntity
1934 | */
1935 | public get alias(): string {
1936 | return this._alias;
1937 | }
1938 | public set alias(value: string) {
1939 | this._alias = value;
1940 | }
1941 | /**
1942 | * Gets or sets the from property of the linkEntity
1943 | */
1944 | public get from(): string {
1945 | return this._from;
1946 | }
1947 | public set from(value: string) {
1948 | this._from = value;
1949 | }
1950 | /**
1951 | * Gets or sets the intersect property of the linkEntity
1952 | */
1953 | public get intersect(): boolean {
1954 | return this._intersect;
1955 | }
1956 | public set intersect(value: boolean) {
1957 | this._intersect = value;
1958 | }
1959 | /**
1960 | * Gets or sets the linktype property of the linkEntity
1961 | */
1962 | public get linktype(): string {
1963 | return this._linktype;
1964 | }
1965 | public set linktype(value: string) {
1966 | this._linktype = value;
1967 | }
1968 | /**
1969 | * Gets or sets the to property of the linkEntity
1970 | */
1971 | public get to(): string {
1972 | return this._to;
1973 | }
1974 | public set to(value: string) {
1975 | this._to = value;
1976 | }
1977 | /**
1978 | * Gets or sets the visible property of the linkEntity
1979 | */
1980 | public get visible(): boolean {
1981 | return this._visible;
1982 | }
1983 | public set visible(value: boolean) {
1984 | this._visible = value;
1985 | }
1986 | /**
1987 | * Gets or sets the allAttributes property of the linkEntity
1988 | */
1989 | public get allAttributes(): boolean {
1990 | return this._allAttributes;
1991 | }
1992 | public set allAttributes(value: boolean) {
1993 | this._allAttributes = value;
1994 | }
1995 | /**
1996 | * Gets or sets the array of attribute of the entity to be returned in the query results
1997 | */
1998 | public get attributes(): Array {
1999 | return this._attributes;
2000 | }
2001 | public set attributes(value: Array) {
2002 | if (!Util.isAttributeArrayOrNull(value)) {
2003 | throw new Error("Sdk.FetchXml.linkEntity.attributes must be an array of Sdk.FetchXml.attribute or null.")
2004 | }
2005 | if (value == null) {
2006 | this._attributes = [];
2007 | } else {
2008 | this._attributes = value;
2009 | }
2010 |
2011 | }
2012 | /**
2013 | * Gets or sets the array of attribute of the entity to be returned in the query results
2014 | */
2015 | public get orders(): Array {
2016 | return this._orders;
2017 | }
2018 | public set orders(value: Array) {
2019 | if (!Util.isOrderArrayOrNull(value)) {
2020 | throw new Error("Sdk.FetchXml.linkEntity.orders must be an array of Sdk.FetchXml.order or null.")
2021 | }
2022 | if (value == null) {
2023 | this._orders = [];
2024 | } else {
2025 | this._orders = value;
2026 | }
2027 |
2028 | }
2029 | /**
2030 | * Gets or sets the array of linkEntity to be applied to the query results
2031 | */
2032 | public get linkEntities(): Array {
2033 | return this._linkEntities;
2034 | }
2035 | public set linkEntities(value: Array) {
2036 | if (!Util.isLinkEntityArrayOrNull(value)) {
2037 | throw new Error("Sdk.FetchXml.linkEntity.linkEntities must be an array of Sdk.FetchXml.linkEntity or null.")
2038 | }
2039 | if (value == null) {
2040 | this._linkEntities = [];
2041 | } else {
2042 | this._linkEntities = value;
2043 | }
2044 | }
2045 | /**
2046 | * Gets or sets the array of filters to be applied to the query results
2047 | */
2048 | public get filters(): Array {
2049 | return this._filters;
2050 | }
2051 | public set filters(value: Array) {
2052 | if (!Util.isFilterArrayOrNull(value)) {
2053 | throw new Error("Sdk.FetchXml.linkEntity.filters must be an array of Sdk.FetchXml.filter or null.")
2054 | }
2055 | if (value == null) {
2056 | this._filters = [];
2057 | } else {
2058 | this._filters = value;
2059 | }
2060 |
2061 | }
2062 | //Internal use only
2063 | public get hash(): string {
2064 | var s = this._name.concat(
2065 | (this._alias ? this._alias : ""),
2066 | (this._from ? this._from : ""),
2067 | (Util.isNullOrUndefined(this._intersect) ? "" : this._intersect.toString()),
2068 | (this._linktype ? this._linktype : ""),
2069 | (this._to ? this._to : ""),
2070 | (Util.isNullOrUndefined(this._visible) ? "" : this._visible.toString()),
2071 | (Util.isNullOrUndefined(this._allAttributes) ? "" : this._allAttributes.toString()),
2072 | (Util.getCollectionHash(this._attributes)),
2073 | (Util.getCollectionHash(this._orders)),
2074 | (Util.getCollectionHash(this._linkEntities)),
2075 | (Util.getCollectionHash(this._filters))
2076 | );
2077 | return s.hashCode();
2078 | }
2079 |
2080 | /** @description Sets the alias property of the linkEntity attribute
2081 | * @param {string} alias The alias value to apply to the linkEntity
2082 | * @returns {Sdk.FetchXml.linkEntity}
2083 | */
2084 | public setAlias(alias) {
2085 | this.alias = alias;
2086 | return this;
2087 | }
2088 |
2089 | /** @description Sets the from property of the linkEntity attribute
2090 | * @param {string} from The from value to apply to the linkEntity
2091 | * @returns {Sdk.FetchXml.linkEntity}
2092 | */
2093 | public setFrom(from) {
2094 | this.from = from;
2095 | return this;
2096 | }
2097 |
2098 | /** @description Sets the intersect property of the linkEntity attribute
2099 | * @param {boolean | null} intersect The intersect value to apply to the linkEntity
2100 | * @returns {Sdk.FetchXml.linkEntity}
2101 | */
2102 | public setIntersect(intersect) {
2103 | this.intersect = intersect;
2104 | return this;
2105 | }
2106 |
2107 | /** @description Sets the name property of the linkEntity attribute
2108 | * @param {string} name The name value to apply to the linkEntity
2109 | * @returns {Sdk.FetchXml.linkEntity}
2110 | */
2111 | public setName(name) {
2112 | this.name = name;
2113 | return this;
2114 | }
2115 |
2116 | /** @description Sets the to property of the linkEntity attribute
2117 | * @param {string} to The to value to apply to the linkEntity
2118 | * @returns {Sdk.FetchXml.linkEntity}
2119 | */
2120 | public setTo(to) {
2121 | this.to = to;
2122 | return this;
2123 | }
2124 |
2125 | /** @description Sets the visible property of the linkEntity attribute
2126 | * @param {boolean | null} visible The visible value to apply to the linkEntity
2127 | * @returns {Sdk.FetchXml.linkEntity}
2128 | */
2129 | public setVisible(visible) {
2130 | this.visible = visible;
2131 | return this;
2132 | }
2133 |
2134 | /** @description Sets the allAttributes property of the linkEntity attribute
2135 | * @param {boolean} allAttributes The allAttributes value to apply to the linkEntity
2136 | * @returns {Sdk.FetchXml.linkEntity}
2137 | */
2138 | public setAllAttributes(allAttributes) {
2139 | this.allAttributes = allAttributes;
2140 | return this;
2141 | }
2142 |
2143 | /** @description Adds an linkEntity to the linkEntities collection
2144 | * @param {Sdk.FetchXml.linkEntity} linkEntity The linkEntity to add to the linkEntities collection
2145 | * @returns {Sdk.FetchXml.linkEntity}
2146 | */
2147 | public addLinkEntity(linkEntity) {
2148 | if (Util.isLinkEntity(linkEntity)) {
2149 | this.linkEntities.push(linkEntity);
2150 | return this;
2151 | }
2152 | throw new Error("Sdk.FetchXml.linkEntity addLinkEntity method linkEntity parameter must be a Sdk.FetchXml.linkEntity value.")
2153 |
2154 | return this;
2155 | }
2156 |
2157 | /** @description Removes a linkEntity from the linkEntities collection by reference
2158 | * @param {Sdk.FetchXml.linkEntity} linkEntity The linkEntity to remove from the linkEntities collection
2159 | * @returns {Sdk.FetchXml.linkEntity}
2160 | */
2161 | public removeLinkEntityByRef(linkEntity) {
2162 | if (!Util.isLinkEntity(linkEntity)) {
2163 | throw new Error("Sdk.FetchXml.linkEntity removeLinkEntityByRef method linkEntity parameter must be an Sdk.FetchXml.linkEntity.")
2164 | }
2165 | Util.removeCollectionValueByRef(this.linkEntities, linkEntity);
2166 |
2167 | return this;
2168 | }
2169 |
2170 | /** @description Removes a linkEntity from the linkEntities collection by value
2171 | * @param {Sdk.FetchXml.linkEntity} linkEntity The linkEntity to remove from the linkEntities collection
2172 | * @returns {Sdk.FetchXml.linkEntity}
2173 | */
2174 | public removeLinkEntity(linkEntity) {
2175 | if (!Util.isLinkEntity(linkEntity)) {
2176 | throw new Error("Sdk.FetchXml.linkEntity removeLinkEntity method linkEntity parameter must be an Sdk.FetchXml.linkEntity.")
2177 | }
2178 | Util.removeCollectionValue(this.linkEntities, linkEntity);
2179 |
2180 | return this;
2181 | }
2182 |
2183 | /** @description Adds an attribute to the attributes collection
2184 | * @param {Sdk.FetchXml.attribute | string} attribute The attribute to add to the attributes collectio
2185 | * @returns {Sdk.FetchXml.linkEntity}
2186 | */
2187 | public addAttribute(attribute) {
2188 | if (Util.isAttribute(attribute)) {
2189 | this.attributes.push(attribute);
2190 | return this;
2191 | }
2192 | if (Util.isString(attribute)) {
2193 | this.attributes.push(new attribute(attribute));
2194 | return this;
2195 | }
2196 | throw new Error("Sdk.FetchXml.linkEntity addAttribute method attribute parameter must be a Sdk.FetchXml.attribute value or a string.")
2197 |
2198 | return this;
2199 | }
2200 |
2201 | /** @description Removes a attribute from the attributes collection by reference
2202 | * @param {Sdk.FetchXml.attribute} attribute The attribute to remove from the attributes collection
2203 | * @returns {Sdk.FetchXml.linkEntity}
2204 | */
2205 | public removeAttributeByRef(attribute) {
2206 | if (!Util.isAttribute(attribute)) {
2207 | throw new Error("Sdk.FetchXml.linkEntity removeAttributeByRef method attribute parameter must be an Sdk.FetchXml.attribute.")
2208 | }
2209 | Util.removeCollectionValueByRef(this.attributes, attribute);
2210 |
2211 | return this;
2212 | }
2213 |
2214 | /** @description Removes a attribute from the attributes collection by value
2215 | * @param {Sdk.FetchXml.attribute} attribute The attribute to remove from the attributes collection
2216 | * @returns {Sdk.FetchXml.linkEntity}
2217 | */
2218 | public removeAttribute(attribute) {
2219 | if (!Util.isAttribute(attribute)) {
2220 | throw new Error("Sdk.FetchXml.linkEntity removeAttribute method attribute parameter must be an Sdk.FetchXml.attribute.")
2221 | }
2222 | Util.removeCollectionValue(this.attributes, attribute);
2223 |
2224 | return this;
2225 | }
2226 |
2227 | /** @description Removes a attribute from the attributes collection by name
2228 | * @param {string} attributeName Name of the attribute to remove from the attributes collection
2229 | * @returns {Sdk.FetchXml.linkEntity}
2230 | */
2231 | public removeAttributeByName(attributeName) {
2232 | if (!Util.isString(attributeName)) {
2233 | throw new Error("Sdk.FetchXml.linkEntity removeAttributeByName method attributeName parameter must be a string.")
2234 | }
2235 | Util.removeCollectionValueByProperty(this.attributes, "name", attributeName)
2236 | return this;
2237 | }
2238 |
2239 | /** @description Adds an order to the orders collection
2240 | * @param {Sdk.FetchXml.order | string} orderOrAttribute The order to add to the attributes collection or the Attribute property of a new order to create
2241 | * @param {boolean} [descending] Whether the order is descending. True if descending, otherwise false
2242 | * @param {string} [alias] The alias to set for the order
2243 | * @returns {Sdk.FetchXml.linkEntity}
2244 | */
2245 | public addOrder(orderOrAttribute: any, descending?, alias?) {
2246 | if (Util.isOrder(orderOrAttribute)) {
2247 | this.orders.push(orderOrAttribute);
2248 | return this;
2249 | }
2250 | if (Util.isString(orderOrAttribute)) {
2251 | this.orders.push(new order(orderOrAttribute, descending, alias));
2252 | return this;
2253 | }
2254 | throw new Error("Sdk.FetchXml.linkEntity addOrder method orderOrAttribute parameter must be a Sdk.FetchXml.order value or a string.")
2255 |
2256 | return this;
2257 | }
2258 |
2259 | /** @description Removes a order from the orders collection by reference
2260 | * @param {Sdk.FetchXml.order} order The order to remove from the orders collection
2261 | * @returns {Sdk.FetchXml.linkEntity}
2262 | */
2263 | public removeOrderByRef(order) {
2264 | if (!Util.isOrder(order)) {
2265 | throw new Error("Sdk.FetchXml.linkEntity removeOrderByRef method order parameter must be an Sdk.FetchXml.order.")
2266 | }
2267 | Util.removeCollectionValueByRef(this.orders, order);
2268 | return this;
2269 | }
2270 |
2271 | /** @description Removes a order from the orders collection by value
2272 | * @param {Sdk.FetchXml.order} order The order to remove from the orders collection
2273 | * @returns {Sdk.FetchXml.linkEntity}
2274 | */
2275 | public removeOrder(order) {
2276 | if (!Util.isOrder(order)) {
2277 | throw new Error("Sdk.FetchXml.linkEntity removeOrder method order parameter must be an Sdk.FetchXml.order.")
2278 | }
2279 | Util.removeCollectionValue(this.orders, order);
2280 | return this;
2281 | }
2282 |
2283 | /** @description Adds an filter to the filters collection
2284 | * @param {Sdk.FetchXml.filter} filter The filter to add to the filters collection
2285 | * @returns {Sdk.FetchXml.linkEntity}
2286 | */
2287 | public addFilter(filter) {
2288 | if (Util.isFilter(filter)) {
2289 | this.filters.push(filter);
2290 | return this;
2291 | }
2292 |
2293 | throw new Error("Sdk.FetchXml.linkEntity addFilter method filter parameter must be a Sdk.FetchXml.filter value.")
2294 |
2295 | return this;
2296 | }
2297 |
2298 | /** @description Removes a filter from the filters collection by reference
2299 | * @param {Sdk.FetchXml.filter} filter The filter to remove from the filters collection
2300 | * @returns {Sdk.FetchXml.linkEntity}
2301 | */
2302 | public removeFilterByRef(filter) {
2303 | if (!Util.isFilter(filter)) {
2304 | throw new Error("Sdk.FetchXml.linkEntity removeFilterByRef method filter parameter must be an Sdk.FetchXml.filter.")
2305 | }
2306 | Util.removeCollectionValueByRef(this.filters, filter);
2307 |
2308 | return this;
2309 | }
2310 |
2311 | /** @description Removes a filter from the filters collection by value
2312 | * @param {Sdk.FetchXml.filter} filter The filter to remove from the filters collection
2313 | * @returns {Sdk.FetchXml.linkEntity}
2314 | */
2315 | public removeFilter(filter) {
2316 | if (!Util.isFilter(filter)) {
2317 | throw new Error("Sdk.FetchXml.linkEntity removeFilter method filter parameter must be an Sdk.FetchXml.filter.")
2318 | }
2319 | Util.removeCollectionValue(this.filters, filter);
2320 |
2321 | return this;
2322 | }
2323 |
2324 | //Internal use only
2325 | toXml(doc: XMLDocument): Node {
2326 |
2327 | var leNode = doc.createElement("link-entity");
2328 | if (this.alias) {
2329 | leNode.setAttribute("alias", this.alias)
2330 | }
2331 | if (this.allAttributes) {
2332 | leNode.appendChild(doc.createElement("all-attributes"));
2333 | }
2334 | if (this.from) {
2335 | leNode.setAttribute("from", this.from)
2336 | }
2337 | if (Util.isBoolean(this.intersect)) {
2338 | leNode.setAttribute("intersect", this.intersect.toString())
2339 | }
2340 | if (this.linktype) {
2341 | leNode.setAttribute("link-type", this.linktype)
2342 | }
2343 | if (this.name) {
2344 | leNode.setAttribute("name", this.name)
2345 | }
2346 | if (this.to) {
2347 | leNode.setAttribute("to", this.to)
2348 | }
2349 | if (Util.isBoolean(this.visible)) {
2350 | leNode.setAttribute("visible", this.visible.toString())
2351 | }
2352 | this.attributes.forEach(function (a) {
2353 | leNode.appendChild(a.toXml(doc));
2354 | })
2355 | this.orders.forEach(function (o) {
2356 | leNode.appendChild(o.toXml(doc));
2357 | })
2358 | this.linkEntities.forEach(function (l) {
2359 | leNode.appendChild(l.toXml(doc));
2360 | })
2361 | this.filters.forEach(function (f) {
2362 | leNode.appendChild(f.toXml(doc));
2363 | })
2364 |
2365 | return leNode;
2366 | }
2367 |
2368 | static linkEntityFromXml(xml) {
2369 | var name = xml.attributes.getNamedItem("name").nodeValue;
2370 | var linkEntityObj = new linkEntity(name);
2371 | linkEntityObj.allAttributes = (xml.getElementsByTagName("all-attributes").length == 1);
2372 |
2373 | Util.parseAttributes(xml, linkEntityObj, (linkEntityObj, name, value) => {
2374 | switch (name) {
2375 | case "to":
2376 | case "from":
2377 | case "alias":
2378 | linkEntityObj[name] = value;
2379 | break;
2380 | case "link-type":
2381 | linkEntityObj.linktype = value;
2382 | break;
2383 | case "visible":
2384 | case "intersect":
2385 | linkEntityObj[name] = (value == "true") ? true : false;
2386 | break;
2387 | default:
2388 | break;
2389 | }
2390 | });
2391 |
2392 | for (var i = 0; i < xml.childNodes.length; i++) {
2393 |
2394 | if (xml.childNodes[i].nodeName == "attribute") {
2395 | linkEntityObj.addAttribute(attribute.attributeFromXml(xml.childNodes[i]));
2396 | }
2397 |
2398 | if (xml.childNodes[i].nodeName == "order") {
2399 | linkEntityObj.addOrder(order.orderFromXml(xml.childNodes[i]));
2400 | }
2401 |
2402 | if (xml.childNodes[i].nodeName == "filter") {
2403 | linkEntityObj.addFilter(filter.filterFromXml(xml.childNodes[i]));
2404 | }
2405 |
2406 | if (xml.childNodes[i].nodeName == "link-entity") {
2407 | linkEntityObj.addLinkEntity(linkEntity.linkEntityFromXml(xml.childNodes[i]));
2408 | }
2409 | }
2410 |
2411 | return linkEntityObj;
2412 | }
2413 |
2414 |
2415 | }
2416 | @sealed
2417 | export class order {
2418 | /**
2419 | * Contains the data for a fetchXml order element.
2420 | * @param attribute The logical name of the attribute
2421 | * @param descending Whether the order is decending. Default is false
2422 | * @param alias The alias to apply to the order
2423 | */
2424 | constructor(attribute?: string, descending?: boolean, alias?: string) {
2425 | // new keyword not required in JS
2426 | if (!(this instanceof order))
2427 | { return new order(attribute, descending, alias) }
2428 |
2429 | if (attribute)
2430 | this.attribute = attribute;
2431 | if (descending)
2432 | this.descending = descending;
2433 | if (alias)
2434 | this.alias = alias;
2435 | }
2436 |
2437 | private _attribute: string = null;
2438 | private _descending: boolean = null;
2439 | private _alias: string = null;
2440 |
2441 | /**
2442 | * Gets or sets logical name of the attribute
2443 | */
2444 | public get attribute(): string {
2445 | return this._attribute;
2446 | }
2447 | public set attribute(value: string) {
2448 | this._attribute = value;
2449 | }
2450 | /**
2451 | *Gets or sets whether the order is descending. Default is false
2452 | */
2453 | public get descending(): boolean {
2454 | return this._descending;
2455 | }
2456 | public set descending(value: boolean) {
2457 | this._descending = value;
2458 | }
2459 | /**
2460 | * Gets or sets the alias property of the order
2461 | */
2462 | public get alias(): string {
2463 | return this._alias;
2464 | }
2465 | public set alias(value: string) {
2466 | this._alias = value;
2467 | }
2468 | //Internal use only
2469 | public get hash(): string {
2470 | var s = "".concat(
2471 | (this._attribute ? this._attribute : ""),
2472 | (this._alias ? this._alias : ""),
2473 | this._descending.toString());
2474 | return s.hashCode();
2475 | }
2476 |
2477 | /** @description Sets the attribute property of the order attribute
2478 | * @param {string} attribute The attribute value to apply to the order
2479 | * @returns {Sdk.FetchXml.order}
2480 | */
2481 | public setAttribute(attribute) {
2482 | this.attribute = attribute;
2483 | return this;
2484 | }
2485 |
2486 | /** @description Sets the alias property of the order attribute
2487 | * @param {string} alias The alias value to apply to the order
2488 | * @returns {Sdk.FetchXml.order}
2489 | */
2490 | public setAlias(alias) {
2491 | this.alias = alias;
2492 | return this;
2493 | }
2494 |
2495 | /** @description Sets the descending property of the order attribute
2496 | * @param {boolean | null} descending The descending value to apply to the order
2497 | * @returns {Sdk.FetchXml.order}
2498 | */
2499 | public setDescending(descending) {
2500 | this.descending = descending;
2501 | return this;
2502 | }
2503 |
2504 | //Internal use only
2505 | toXml(doc: XMLDocument): Node {
2506 | var orderNode = doc.createElement("order");
2507 | if (this.attribute) {
2508 | orderNode.setAttribute("attribute", this.attribute)
2509 | }
2510 | if (this.alias) {
2511 | orderNode.setAttribute("alias", this.alias)
2512 | }
2513 | if (!Util.isNullOrUndefined(this.descending)) {
2514 | orderNode.setAttribute("descending", this.descending.toString())
2515 | }
2516 | return orderNode;
2517 | }
2518 |
2519 |
2520 | static orderFromXml(xml) {
2521 | var orderObj = new order();
2522 | Util.parseAttributes(xml, orderObj, (orderObj, name, value) => {
2523 | switch (name) {
2524 | case "attribute":
2525 | orderObj.attribute = value;
2526 | break;
2527 | case "alias":
2528 | orderObj.alias = value;
2529 | break;
2530 | case "descending":
2531 | orderObj.descending = (value == "true") ? true : false;
2532 | break;
2533 | default:
2534 | break;
2535 | }
2536 | });
2537 | return orderObj;
2538 | }
2539 | }
2540 | @sealed
2541 | export class value {
2542 | /**
2543 | * Contains the data for a fetchXml value element.
2544 | * @param value The the value of the value
2545 | * @param [uiname] The uiname for the value
2546 | * @param [uitype] The uitype for the value
2547 | */
2548 | constructor(value: any, uiname?: string, uitype?: string) {
2549 | //New keyword not required in JS
2550 | if (!(this instanceof Sdk.FetchXml.value))
2551 | { return new value(value, uiname, uitype) }
2552 |
2553 | if (value)
2554 | this.value = value;
2555 | if (uiname)
2556 | this.uiname = uiname;
2557 | if (uitype)
2558 | this.uitype = uitype;
2559 | }
2560 |
2561 | private _value: any = null;
2562 | private _uiname: string = null;
2563 | private _uitype: string = null;
2564 |
2565 |
2566 | /**
2567 | * Gets or sets the value for the value.
2568 | */
2569 | public get value(): any {
2570 | return this._value;
2571 | }
2572 | public set value(value: any) {
2573 | this._value = value;
2574 | }
2575 | /**
2576 | * Gets or sets the uiname to apply to the value
2577 | */
2578 | public get uiname(): string {
2579 | return this._uiname;
2580 | }
2581 | public set uiname(value: string) {
2582 | this._uiname = value;
2583 | }
2584 | /**
2585 | * Gets or sets the uitype to apply to the value
2586 | */
2587 | public get uitype(): string {
2588 | return this._uitype;
2589 | }
2590 | public set uitype(value: string) {
2591 | this._uitype = value;
2592 | }
2593 |
2594 | /** @description Sets the value to apply in the value
2595 | * @param {string} value The value to apply in the value
2596 | * @returns {Sdk.FetchXml.value}
2597 | */
2598 | public setValue(value) {
2599 | this.value = value;
2600 | return this;
2601 | }
2602 |
2603 | /** @description Sets the uiname to apply in the value
2604 | * @param {string} uiname The uiname to apply in the value
2605 | * @returns {Sdk.FetchXml.value}
2606 | */
2607 | public setUIname(value) {
2608 | this.uiname = value;
2609 | return this;
2610 | }
2611 |
2612 | /** @description Sets the uitype to apply in the value
2613 | * @param {string} uitype The uitype to apply in the value
2614 | * @returns {Sdk.FetchXml.value}
2615 | */
2616 | public setUItype(value) {
2617 | this.uitype = value;
2618 | return this;
2619 | }
2620 |
2621 | //Internal use only
2622 | toXml(doc: XMLDocument): Node {
2623 |
2624 | var vNode = doc.createElement("value");
2625 | if (this.uitype) {
2626 | vNode.setAttribute("uitype", this.uitype)
2627 | }
2628 | if (this.uiname) {
2629 | vNode.setAttribute("uiname", this.uiname)
2630 | }
2631 | vNode.appendChild(doc.createTextNode(this.value));
2632 | return vNode;
2633 | }
2634 |
2635 | static valueFromXml(xml) {
2636 |
2637 | var valueObj = new value(xml.textContent);
2638 | Util.parseAttributes(xml, valueObj, (object, name, value) => {
2639 | switch (name) {
2640 | case "uiname":
2641 | case "uitype":
2642 | object[name] = value;
2643 | break;
2644 | }
2645 | });
2646 |
2647 | return valueObj;
2648 | }
2649 |
2650 | }
2651 | export class Util {
2652 | public static isBoolean(obj) {
2653 | return (typeof obj === "boolean");
2654 | }
2655 | public static isBooleanOrNull(obj) {
2656 | return (Util.isNull(obj) || Util.isBoolean(obj))
2657 | }
2658 | public static isNumber(obj) {
2659 | return (typeof (obj) === "number");
2660 | }
2661 | public static isNumberOrNull(obj) {
2662 | return (Util.isNull(obj) || Util.isNumber(obj))
2663 | }
2664 | public static isNull(obj) {
2665 | return (obj === null);
2666 | }
2667 | public static isNullOrUndefined(obj) {
2668 | return (obj === null || typeof obj == "undefined");
2669 | }
2670 | public static isEnumMember(enumType, obj) {
2671 | for (var i in enumType) {
2672 | if (obj === enumType[i]) {
2673 | return true;
2674 | }
2675 | }
2676 | return false;
2677 | }
2678 | public static isEnumMemberOrNull(enumType, obj) {
2679 | return (Util.isNull(obj) || Util.isEnumMember(enumType, obj));
2680 | }
2681 | public static isString(obj) {
2682 | return (typeof obj === "string");
2683 | }
2684 | public static isStringOrNull(obj) {
2685 | return (Util.isNull(obj) || Util.isString(obj));
2686 | }
2687 | public static isOrder(obj) {
2688 | return (obj instanceof order)
2689 | }
2690 | public static isOrderOrNull(obj) {
2691 | return (Util.isNull(obj) || Util.isOrder(obj));
2692 | }
2693 | public static isOrderArray(obj) {
2694 | if (Array.isArray(obj)) {
2695 | obj.forEach(function (item) {
2696 | if (!Util.isOrder(item)) {
2697 | return false;
2698 | }
2699 | })
2700 | return true;
2701 | }
2702 | return false;
2703 | }
2704 | public static isOrderArrayOrNull(obj) {
2705 | return (Util.isNull(obj) || Util.isOrderArray(obj));
2706 | }
2707 | public static isEntity(obj) {
2708 | return (obj instanceof entity)
2709 | }
2710 | public static isAttribute(obj) {
2711 | return (obj instanceof attribute)
2712 | }
2713 | public static isAttributeArray(obj) {
2714 | if (Array.isArray(obj)) {
2715 | obj.forEach(function (item) {
2716 | if (!Util.isAttribute(item)) {
2717 | return false;
2718 | }
2719 | })
2720 | return true;
2721 | }
2722 | return false;
2723 | }
2724 | public static isAttributeArrayOrNull(obj) {
2725 | return (Util.isNull(obj) || Util.isAttributeArray(obj));
2726 | }
2727 | public static isLinkEntity(obj) {
2728 | return (obj instanceof linkEntity)
2729 | }
2730 | public static isLinkEntityOrNull(obj) {
2731 | return (Util.isNull(obj) || Util.isLinkEntity(obj));
2732 | }
2733 | public static isLinkEntityArray(obj) {
2734 | if (Array.isArray(obj)) {
2735 | obj.forEach(function (item) {
2736 | if (!Util.isLinkEntity(item)) {
2737 | return false;
2738 | }
2739 | })
2740 | return true;
2741 | }
2742 | return false;
2743 | }
2744 | public static isLinkEntityArrayOrNull(obj) {
2745 | return (Util.isNull(obj) || Util.isLinkEntityArray(obj));
2746 | }
2747 | public static isFilter(obj) {
2748 | return (obj instanceof filter)
2749 | }
2750 | public static isFilterOrNull(obj) {
2751 | return (Util.isNull(obj) || Util.isFilter(obj));
2752 | }
2753 | public static isFilterArray(obj) {
2754 | if (Array.isArray(obj)) {
2755 | obj.forEach(function (item) {
2756 | if (!Util.isFilter(item)) {
2757 | return false;
2758 | }
2759 | })
2760 | return true;
2761 | }
2762 | return false;
2763 | }
2764 | public static isFilterArrayOrNull(obj) {
2765 | return (Util.isNull(obj) || Util.isFilterArray(obj));
2766 | }
2767 | public static isCondition(obj) {
2768 | return (obj instanceof condition)
2769 | }
2770 | public static isConditionOrNull(obj) {
2771 | return (Util.isNull(obj) || Util.isCondition(obj));
2772 | }
2773 | public static isConditionArray(obj) {
2774 | if (Array.isArray(obj)) {
2775 | obj.forEach(function (item) {
2776 | if (!Util.isCondition(item)) {
2777 | return false;
2778 | }
2779 | })
2780 | return true;
2781 | }
2782 | return false;
2783 | }
2784 | public static isConditionArrayOrNull(obj) {
2785 | return (Util.isNull(obj) || Util.isConditionArray(obj));
2786 | }
2787 | public static isValue(obj) {
2788 | return (obj instanceof value)
2789 | }
2790 | public static isValueOrNull(obj) {
2791 | return (Util.isNull(obj) || Util.isValue(obj));
2792 | }
2793 | public static isValueArray(obj) {
2794 | if (Array.isArray(obj)) {
2795 | var returnValue = true;
2796 | obj.forEach(function (item) {
2797 | if (!Util.isValue(item)) {
2798 | returnValue = false;
2799 | }
2800 | })
2801 | return returnValue;
2802 | }
2803 | return false;
2804 | }
2805 | public static isValueArrayOrNull(obj) {
2806 | return (Util.isNull(obj) || Util.isValueArray(obj));
2807 | }
2808 | public static getEnumNameFromValue(enumtype, value) {
2809 | for (var i in enumtype) {
2810 | if (enumtype[i] == value) {
2811 | return i;
2812 | }
2813 | }
2814 | }
2815 | public static getCollectionHash(collection) {
2816 | var ch = [];
2817 | collection.forEach(function (c) {
2818 | ch.push(c.hash)
2819 | });
2820 | return ch.join();
2821 | }
2822 | public static removeCollectionValue(collection, value) {
2823 | Util.removeCollectionValueByProperty(collection, "hash", value)
2824 | }
2825 | public static removeCollectionValueByProperty(collection, propertyName, value) {
2826 | var matches = [];
2827 | collection.forEach(function (b, i) {
2828 | //Check if same values
2829 | if (b[propertyName] == value[propertyName]) {
2830 | matches.push(b);
2831 | }
2832 | });
2833 | matches.forEach(function (m) {
2834 | Util.removeCollectionValueByRef(collection, m);
2835 | });
2836 |
2837 | }
2838 | public static removeCollectionValueByRef(collection, value) {
2839 | var indexes = [];
2840 | collection.forEach(function (a, i) {
2841 | //check if same object
2842 | if (a === value) {
2843 | indexes.push(i);
2844 | }
2845 | });
2846 | if (indexes.length > 0) {
2847 | //Removing in reverse order
2848 | for (var i = indexes.length - 1; i >= 0; i--) {
2849 | collection.splice(indexes[i], 1);
2850 | }
2851 | }
2852 | }
2853 | public static convertFetchBoolType(value) {
2854 | switch (value) {
2855 | case "true":
2856 | case "1":
2857 | return true;
2858 | case "false":
2859 | case "0":
2860 | return false;
2861 | default:
2862 | throw new Error("Unexpected FetchBoolType value");
2863 | break;
2864 | }
2865 | }
2866 | public static parseAttributes(xml: Node, object: Object, switchFunction: Function) {
2867 | var atts = xml.attributes;
2868 | for (var i = 0; i < atts.length; i++) {
2869 | var name = atts[i].nodeName;
2870 | var value = atts[i].nodeValue;
2871 | switchFunction(object, name, value)
2872 | }
2873 | }
2874 | }
2875 | @frozen
2876 | export class Mapping {
2877 | static Internal = "internal";
2878 | static Logical = "logical";
2879 | }
2880 | @frozen
2881 | export class OutputFormat {
2882 | static Ado = "xml-ado";
2883 | static Auto = "xml-auto";
2884 | static Elements = "xml-elements";
2885 | static Raw = "xml-raw";
2886 | static Platform = "xml-platform";
2887 | }
2888 | @frozen
2889 | export class Build {
2890 |
2891 | static OnePoint504021 = "1.504021";
2892 | static OnePoint003017 = "1.003017";
2893 | }
2894 | @frozen
2895 | export class Aggregate {
2896 | static Count = "count";
2897 | static CountColumn = "countcolumn";
2898 | static Sum = "sum";
2899 | static Avg = "avg";
2900 | static Min = "min";
2901 | static Max = "max";
2902 | }
2903 | @frozen
2904 | export class RowAggregate {
2905 | static Countchildren = "countchildren";
2906 | }
2907 | @frozen
2908 | export class DateGrouping {
2909 | static Day = "day";
2910 | static Week = "week";
2911 | static Month = "month";
2912 | static Quarter = "quarter";
2913 | static Year = "year";
2914 | static FiscalPeriod = "fiscal-period";
2915 | static FiscalYear = "fiscal-year";
2916 | }
2917 | @frozen
2918 | export class Operator {
2919 | /** Returns all records in referenced record's hierarchical ancestry line.*/
2920 | static Above = "above";
2921 | /** The string occurs at the beginning of another string.*/
2922 | static BeginsWith = "begins-with";
2923 | /** The value is between two values.*/
2924 | static Between = "between";
2925 | /** The string ends with another string.*/
2926 | static EndsWith = "ends-with";
2927 | /** The values are compared for equality. */
2928 | static Equal = "eq";
2929 | /** The value is equal to the specified business ID. */
2930 | static EqualBusinessId = "eq-businessid";
2931 | /** Returns the referenced record and all records above it in the hierarchy.*/
2932 | static EqualOrAbove = "eq-or-above";
2933 | /** Returns the referenced record and all records below it in the hierarchy.*/
2934 | static EqualOrUnder = "eq-or-under";
2935 | /** The value is equal to the specified user ID.*/
2936 | static EqualUserId = "eq-userid";
2937 | /** The value is equal to the language for the user. */
2938 | static EqualUserLanguage = "eq-userlanguage";
2939 | /** When hierarchical security models are used; Equals current user or his reporting hierarchy*/
2940 | static EqualUserOrUserHierarchy = "eq-useroruserhierarchy";
2941 | /** When hierarchical security models are used; Equals current user and his teams or his reporting hierarchy and their teams*/
2942 | static EqualUserOrUserHierarchyAndTeams = "eq-useroruserhierarchyandteams";
2943 | /** The record is owned by a user or teams that the user is a member of.*/
2944 | static EqualUserOrUserTeams = "eq-useroruserteams";
2945 | /** The record is owned by teams that the user is a member of.*/
2946 | static EqualUserTeams = "eq-userteams";
2947 | /** The value is greater than or equal to the compared value.*/
2948 | static GreaterOrEqual = "ge";
2949 | /** The value is greater than the compared value.*/
2950 | static GreaterThan = "gt";
2951 | /** The value exists in a list of values.*/
2952 | static In = "in";
2953 | /** The value is within the specified fiscal period.*/
2954 | static InFiscalPeriod = "in-fiscal-period";
2955 | /** The value is within the specified fiscal period and year.*/
2956 | static InFiscalPeriodAndYear = "in-fiscal-period-and-year";
2957 | /** The value is within the specified year.*/
2958 | static InFiscalYear = "in-fiscal-year";
2959 | /** The value is within or after the specified fiscal period and year.*/
2960 | static InOrAfterFiscalPeriodAndYear = "in-or-after-fiscal-period-and-year";
2961 | /** The value is within or before the specified fiscal period and year.*/
2962 | static InOrBeforeFiscalPeriodAndYear = "in-or-before-fiscal-period-and-year";
2963 | /** The value is within the last fiscal period.*/
2964 | static LastFiscalPeriod = "last-fiscal-period";
2965 | /** The value is within the last fiscal year.*/
2966 | static LastFiscalYear = "last-fiscal-year";
2967 | /** The value is within the last month*/
2968 | static LastMonth = "last-month";
2969 | /** The value is within last seven days.*/
2970 | static LastSevenDays = "last-seven-days";
2971 | /** The value is within the previous week*/
2972 | static LastWeek = "last-week";
2973 | /** The value is within last X days.*/
2974 | static LastXDays = "last-x-days";
2975 | /** The value is within the last X fiscal periods.*/
2976 | static LastXFiscalPeriods = "last-x-fiscal-periods";
2977 | /** The value is within the last X fiscal years.*/
2978 | static LastXFiscalYears = "last-x-fiscal-years";
2979 | /** The value is within the last X hours.*/
2980 | static LastXHours = "last-x-hours";
2981 | /** The value is within the last X months.*/
2982 | static LastXMonths = "last-x-months";
2983 | /** The value is within the last X weeks.*/
2984 | static LastXWeeks = "last-x-weeks";
2985 | /** The value is within the last X years.*/
2986 | static LastXYears = "last-x-years";
2987 | /** The value is within the last year.*/
2988 | static LastYear = "last-year";
2989 | /** The value is less than or equal to the compared value.*/
2990 | static LessOrEqual = "le";
2991 | /** The character string is matched to the specified pattern.*/
2992 | static Like = "like";
2993 | /** The value is less than the compared value.*/
2994 | static LessThan = "lt";
2995 | /** The two values are not equal.*/
2996 | static NotEqual = "ne";
2997 | /** The value is not equal to the specified business ID.*/
2998 | static NotEqualBusinessId = "ne-businessid";
2999 | /** The value is not equal to the specified user ID.*/
3000 | static NotEqualUserId = "ne-userid";
3001 | /** Not Equal To*/
3002 | static Neq = "neq"; //Is this the same as 'ne'?
3003 | /** The value is within the next fiscal period.*/
3004 | static NextFiscalPeriod = "next-fiscal-period";
3005 | /** The value is within the next fiscal year.*/
3006 | static NextFiscalYear = "next-fiscal-year";
3007 | /** The value is within the next month.*/
3008 | static NextMonth = "next-month";
3009 | /** The value is within the next seven days.*/
3010 | static NextSevenDays = "next-seven-days";
3011 | /** The value is within the next week.*/
3012 | static NextWeek = "next-week";
3013 | /** The value is within the X days.*/
3014 | static NextXDays = "next-x-days";
3015 | /** The value is within the next X fiscal periods.*/
3016 | static NextXFiscalPeriods = "next-x-fiscal-periods";
3017 | /** The value is within the next X fiscal years.*/
3018 | static NextXFiscalYears = "next-x-fiscal-years";
3019 | /** The value is within the next X hours.*/
3020 | static NextXHours = "next-x-hours";
3021 | /** The value is within the next X nonths.*/
3022 | static NextXMonths = "next-x-months";
3023 | /** The value is within the next X weeks.*/
3024 | static NextXWeeks = "next-x-weeks";
3025 | /** The value is within the next X years.*/
3026 | static NextXYears = "next-x-years";
3027 | /** The value is within the next year.*/
3028 | static NextYear = "next-year";
3029 | /** The string does not begin with another string.*/
3030 | static NotBeginWith = "not-begin-with";
3031 | /** The value is not between two values.*/
3032 | static NotBetween = "not-between";
3033 | /** The string does not end with another string.*/
3034 | static NotEndWith = "not-end-with";
3035 | /** The given value is not matched to a value in a subquery or a list.*/
3036 | static NotIn = "not-in";
3037 | /** The character string does not match the specified pattern.*/
3038 | static NotLike = "not-like";
3039 | /** The value is not null.*/
3040 | static NotNull = "not-null";
3041 | /** Returns all records not below the referenced record in the hierarchy*/
3042 | static NotUnder = "not-under";
3043 | /** The value is null.*/
3044 | static Null = "null";
3045 | /** The value is older than the specified number of days. */
3046 | static OlderThanXDays = "olderthan-x-days";
3047 | /** The value is older than the specified number of hours. */
3048 | static OlderThanXHours = "olderthan-x-hours";
3049 | /** The value is older than the specified number of minutes. */
3050 | static OlderThanXMinutes = "olderthan-x-minutes";
3051 | /** The value is older than the specified number of months. */
3052 | static OlderThanXMonths = "olderthan-x-months";
3053 | /** The value is older than the specified number of weeks. */
3054 | static OlderThanXWeeks = "olderthan-x-weeks";
3055 | /** The value is older than the specified number of years. */
3056 | static OlderThanXYears = "olderthan-x-years";
3057 | /** The value is on a specified date.*/
3058 | static On = "on";
3059 | /** The value is on or after a specified date.*/
3060 | static OnOrAfter = "on-or-after";
3061 | /** The value is on or before a specified date.*/
3062 | static OnOrBefore = "on-or-before";
3063 | /** The value is within the current fiscal period.*/
3064 | static ThisFiscalPeriod = "this-fiscal-period";
3065 | /** The value is within the current fiscal year.*/
3066 | static ThisFiscalYear = "this-fiscal-year";
3067 | /** The value is within the current month.*/
3068 | static ThisMonth = "this-month";
3069 | /** The value is within the current week.*/
3070 | static ThisWeek = "this-week";
3071 | /** The value is within the current year.*/
3072 | static ThisYear = "this-year";
3073 | /** The value equals today’s date.*/
3074 | static Today = "today";
3075 | /** The value equals tomorrow’s date.*/
3076 | static Tomorrow = "tomorrow";
3077 | /** Returns all child records below the referenced record in the hierarchy*/
3078 | static Under = "under";
3079 | /** The value equals yesterday’s date.*/
3080 | static Yesterday = "yesterday";
3081 | }
3082 | @frozen
3083 | export class FilterType {
3084 | static And = "and";
3085 | static Or = "or";
3086 | }
3087 | }
3088 |
3089 | function sealed(constructor: Function) {
3090 | Object.seal(constructor);
3091 | Object.seal(constructor.prototype);
3092 | }
3093 | function frozen(constructor: Function) {
3094 | Object.freeze(constructor);
3095 | Object.freeze(constructor.prototype);
3096 | }
3097 |
3098 | /*
3099 | Hash Generator modified from
3100 | http://stackoverflow.com/questions/7616461/generate-a-hash-from-string-in-javascript-jquery
3101 | http://werxltd.com/wp/2010/05/13/javascript-implementation-of-javas-string-hashcode-method/
3102 | */
3103 |
3104 | interface String {
3105 | hashCode: () => string;
3106 | }
3107 |
3108 | String.prototype.hashCode = function (): string {
3109 | let hash = 0;
3110 | if (this.length == 0) return hash.toString();
3111 | for (let i = 0; i < this.length; i++) {
3112 | let char = this.charCodeAt(i);
3113 | hash = ((hash << 5) - hash) + char;
3114 | hash = hash & hash; // Convert to 32bit integer
3115 | }
3116 | return hash.toString();
3117 | }
--------------------------------------------------------------------------------