UNPKG

@arcgis/core

Version:

ArcGIS Maps SDK for JavaScript: A complete 2D and 3D mapping and data visualization API

6 lines (5 loc) • 14 kB
/* All material copyright ESRI, All Rights Reserved, unless otherwise specified. See https://js.arcgis.com/4.32/esri/copyright.txt for details. */ import e from"../../../Graphic.js";import{cloneGeometry as t}from"../../kernel.js";import{FeatureSetError as r,FeatureSetErrorCodes as s}from"../support/errorsupport.js";import a from"../support/FeatureSet.js";import i from"../support/IdSet.js";import{cloneField as l,FeatureServiceDatabaseType as n,isDate as o,isLuxonDate as u,isArcadeTime as h,isArcadeDate as c,isArcadeDateOnly as d,layerGeometryEsriConstants as p}from"../support/shared.js";import{reformulateWithoutField as f,toWhereClause as g,translateFunctionToDatabaseSpecific as N,convertColumnReferenceToSql as _,makeToday as S,makeSqlFromDateTimeParameter as m,makeTimeString as w,arcadeDateToSqlString as v,arcadeDateOnlyToSqlString as C,convertIntervalToSql as T,combine as F,scanForField as W}from"../support/sqlUtils.js";import{assertIsSome as y}from"../../../core/maybe.js";import{SqlError as A,SqlErrorCodes as E}from"../../../core/sql/errorSupport.js";import x from"../../../core/sql/WhereClause.js";import D from"../../../geometry/SpatialReference.js";class I{constructor(e){this.field=e,this.sqlRewritable=!1}postInitialization(e,t){}}class k extends I{constructor(e){super(e),this.sqlRewritable=!0}extractValue(e){return e.attributes[this.field.name]}rewriteSql(e){return{rewritten:this.sqlRewritable,where:e}}}class b extends I{constructor(e,t,r){super(l(e)),this.originalField=e,this.sqlRewritable=!0,this.field.name=t,this.field.alias=r}rewriteSql(e,t){return{rewritten:this.sqlRewritable,where:f(e,this.field.name,this.originalField.name,t.getFieldsIndex())}}extractValue(e){return e.attributes[this.originalField.name]}}class B extends I{constructor(e,t,r){super(e),this.codefield=t,this.lkp=r,this.reverseLkp={};for(const s in r)this.reverseLkp[r[s]]=s;this.sqlRewritable=!0}rewriteSql(e,t){const r=this.evaluateNodeToWhereClause(e.parseTree,n.Standardised,this.field.name,this.codefield instanceof x?g(this.codefield,n.Standardised):this.codefield,e.parameters);return r.includes(B.BADNESS)?{rewritten:!1,where:e}:{rewritten:this.sqlRewritable,where:x.create(r,{fieldsIndex:t._parent.getFieldsIndex(),timeZone:t.dateFieldsTimeZoneDefaultUTC})}}evaluateNodeToWhereClause(e,t,r=null,s=null,a){let i,l,n,p;switch(e.type){case"interval":return T(this.evaluateNodeToWhereClause(e.value,t,r,s,a),e.qualifier,e.op);case"case-expression":{let s=" CASE ";"simple"===e.format&&(s+=this.evaluateNodeToWhereClause(e.operand,t,r,B.BADNESS,a));for(let i=0;i<e.clauses.length;i++)s+=" WHEN "+this.evaluateNodeToWhereClause(e.clauses[i].operand,t,r,B.BADNESS,a)+" THEN "+this.evaluateNodeToWhereClause(e.clauses[i].value,t,r,B.BADNESS,a);return null!==e.else&&(s+=" ELSE "+this.evaluateNodeToWhereClause(e.else,t,r,B.BADNESS,a)),s+=" END ",s}case"parameter":{const r=a[e.value.toLowerCase()];if("string"==typeof r)return"'"+r.toString().replaceAll("'","''")+"'";if(o(r))return m(r,t);if(u(r))return m(r,t);if(h(r))return w(r,t);if(c(r))return v(r,t);if(d(r))return C(r,t);if(Array.isArray(r)){const e=[];for(let s=0;s<r.length;s++)"string"==typeof r[s]?e.push("'"+r[s].toString().replaceAll("'","''")+"'"):o(r[s])||u(r[s])?e.push(m(r[s],t)):h(r[s])?e.push(w(r[s],t)):c(r[s])?e.push(v(r[s],t)):d(r[s])?e.push(C(r[s],t)):e.push(r[s].toString());return e}return r.toString()}case"expression-list":l=[];for(const i of e.value)l.push(this.evaluateNodeToWhereClause(i,t,r,s,a));return l;case"unary-expression":return" ( NOT "+this.evaluateNodeToWhereClause(e.expr,t,r,B.BADNESS,a)+" ) ";case"binary-expression":switch(e.operator){case"AND":return" ("+this.evaluateNodeToWhereClause(e.left,t,r,s,a)+" AND "+this.evaluateNodeToWhereClause(e.right,t,r,s,a)+") ";case"OR":return" ("+this.evaluateNodeToWhereClause(e.left,t,r,s,a)+" OR "+this.evaluateNodeToWhereClause(e.right,t,r,s,a)+") ";case"IS":if("null"!==e.right.type)throw new A(E.UnsupportedIsRhs);return" ("+this.evaluateNodeToWhereClause(e.left,t,r,s,a)+" IS NULL )";case"ISNOT":if("null"!==e.right.type)throw new A(E.UnsupportedIsRhs);return" ("+this.evaluateNodeToWhereClause(e.left,t,r,s,a)+" IS NOT NULL )";case"IN":if(i=[],"expression-list"===e.right.type){if("column-reference"===e.left.type&&e.left.column.toUpperCase()===this.field.name.toUpperCase()){const i=[];let l=!0;for(const t of e.right.value){if("string"!==t.type){l=!1;break}if(void 0===this.lkp[t.value]){l=!1;break}i.push(this.lkp[t.value].toString())}if(l)return" ("+this.evaluateNodeToWhereClause(e.left,t,r,s,a)+" IN ("+i.join(",")+")) "}return i=this.evaluateNodeToWhereClause(e.right,t,r,s,a)," ("+this.evaluateNodeToWhereClause(e.left,t,r,s,a)+" IN ("+i.join(",")+")) "}return p=this.evaluateNodeToWhereClause(e.right,t,r,s,a),Array.isArray(p)?" ("+this.evaluateNodeToWhereClause(e.left,t,r,s,a)+" IN ("+p.join(",")+")) ":" ("+this.evaluateNodeToWhereClause(e.left,t,r,s,a)+" IN ("+p+")) ";case"NOT IN":if(i=[],"expression-list"===e.right.type){if("column-reference"===e.left.type&&e.left.column.toUpperCase()===this.field.name.toUpperCase()){const i=[];let l=!0;for(const t of e.right.value){if("string"!==t.type){l=!1;break}if(void 0===this.lkp[t.value]){l=!1;break}i.push(this.lkp[t.value].toString())}if(l)return" ("+this.evaluateNodeToWhereClause(e.left,t,r,s,a)+" NOT IN ("+i.join(",")+")) "}return i=this.evaluateNodeToWhereClause(e.right,t,r,s,a)," ("+this.evaluateNodeToWhereClause(e.left,t,r,s,a)+" NOT IN ("+i.join(",")+")) "}return p=this.evaluateNodeToWhereClause(e.right,t,r,s,a),Array.isArray(p)?" ("+this.evaluateNodeToWhereClause(e.left,t,r,s,a)+" NOT IN ("+p.join(",")+")) ":" ("+this.evaluateNodeToWhereClause(e.left,t,r,s,a)+" NOT IN ("+p+")) ";case"BETWEEN":return n=this.evaluateNodeToWhereClause(e.right,t,r,B.BADNESS,a)," ("+this.evaluateNodeToWhereClause(e.left,t,r,B.BADNESS,a)+" BETWEEN "+n[0]+" AND "+n[1]+" ) ";case"NOTBETWEEN":return n=this.evaluateNodeToWhereClause(e.right,t,r,B.BADNESS,a)," ("+this.evaluateNodeToWhereClause(e.left,t,r,B.BADNESS,a)+" NOT BETWEEN "+n[0]+" AND "+n[1]+" ) ";case"LIKE":return""!==e.escape?" ("+this.evaluateNodeToWhereClause(e.left,t,r,B.BADNESS,a)+" LIKE "+this.evaluateNodeToWhereClause(e.right,t,r,B.BADNESS,a)+" ESCAPE '"+e.escape+"') ":" ("+this.evaluateNodeToWhereClause(e.left,t,r,B.BADNESS,a)+" LIKE "+this.evaluateNodeToWhereClause(e.right,t,r,B.BADNESS,a)+") ";case"NOT LIKE":return""!==e.escape?" ("+this.evaluateNodeToWhereClause(e.left,t,r,B.BADNESS,a)+" NOT LIKE "+this.evaluateNodeToWhereClause(e.right,t,r,B.BADNESS,a)+" ESCAPE '"+e.escape+"') ":" ("+this.evaluateNodeToWhereClause(e.left,t,r,B.BADNESS,a)+" NOT LIKE "+this.evaluateNodeToWhereClause(e.right,t,r,B.BADNESS,a)+") ";case"<>":case"=":if("column-reference"===e.left.type&&"string"===e.right.type){if(e.left.column.toUpperCase()===this.field.name.toUpperCase()&&void 0!==this.lkp[e.right.value.toString()])return" ("+s+" "+e.operator+" "+this.lkp[e.right.value.toString()].toString()+") "}else if("column-reference"===e.right.type&&"string"===e.left.type&&e.right.column.toUpperCase()===this.field.name.toUpperCase())return" ("+this.lkp[e.right.value.toString()].toString()+" "+e.operator+" "+s+") ";return" ("+this.evaluateNodeToWhereClause(e.left,t,r,B.BADNESS,a)+" "+e.operator+" "+this.evaluateNodeToWhereClause(e.right,t,r,B.BADNESS,a)+") ";case"<":case">":case">=":case"<=":case"*":case"-":case"+":case"/":case"||":return" ("+this.evaluateNodeToWhereClause(e.left,t,r,B.BADNESS,a)+" "+e.operator+" "+this.evaluateNodeToWhereClause(e.right,t,r,B.BADNESS,a)+") "}case"null":return"null";case"boolean":return!0===e.value?"1":"0";case"string":return"'"+e.value.toString().replaceAll("'","''")+"'";case"timestamp":return`timestamp '${e.value}'`;case"date":return`date '${e.value}'`;case"time":return`time '${e.value}'`;case"number":return e.value.toString();case"current-time":return S(e.mode,t);case"current-user":return"CURRENT_USER";case"column-reference":return r&&r.toLowerCase()===e.column.toLowerCase()?"("+s+")":_(e.column);case"data-type":return e.value;case"function":{const s=this.evaluateNodeToWhereClause(e.args,t,r,B.BADNESS,a);return N(e.name,s,t)}}throw new A(E.UnsupportedSyntax,{node:e.type})}extractValue(e){return this.codefield instanceof x?this.reverseLkp[x.convertValueToStorageFormat(this.codefield.calculateValueCompiled(e))]:this.reverseLkp[e.attributes[this.codefield]]}}B.BADNESS="_!!!_BAD_LKP_!!!!";class L extends I{constructor(e,t){super(e),this._sql=t}rewriteSql(e,t){return{rewritten:!0,where:f(e,this.field.name,g(this._sql,n.Standardised),t.getFieldsIndex())}}extractValue(e){return x.convertValueToStorageFormat(this._sql.calculateValueCompiled(e),this.field.type)}}class R extends a{static findField(e,t){for(const r of e)if(r.name.toLowerCase()===t.toString().toLowerCase())return r;return null}constructor(e){super(e),this._calcFunc=null,this.declaredClass="esri.arcade.featureset.actions.Adapted",this.adaptedFields=[],this._extraFilter=null,this._extraFilter=e.extraFilter,this._parent=e.parentfeatureset,this._maxProcessing=30,this.adaptedFields=e.adaptedFields}_initialiseFeatureSet(){null!==this._parent?(this.geometryType=this._parent.geometryType,this.objectIdField=this._parent.objectIdField,this.globalIdField=this._parent.globalIdField,this.spatialReference=this._parent.spatialReference,this.hasM=this._parent.hasM,this.hasZ=this._parent.hasZ,this.typeIdField=this._parent.typeIdField,this.types=this._parent.types):(this.spatialReference=new D({wkid:4326}),this.objectIdField="",this.globalIdField="",this.geometryType=p.point,this.typeIdField="",this.types=null,this.subtypeField=null,this.subtypes=null),this.fields=[];for(const e of this.adaptedFields)e.postInitialization(this,this._parent),this.fields.push(e.field)}async _getSet(e){if(null===this._wset){await this._ensureLoaded();let t=null;return t=this._extraFilter?await this._getFilteredSet("",null,null,null,e):await(this._parent?._getSet(e)),this._checkCancelled(e),y(t),this._wset=new i(t._candidates.slice(),t._known.slice(),t._ordered,this._clonePageDefinition(t.pagesDefinition)),this._wset}return this._wset}_isInFeatureSet(e){return this._parent._isInFeatureSet(e)}async _getFeatures(r,s,a,l){const n=[];-1!==s&&void 0===this._featureCache[s]&&n.push(s);const o=this._maxQueryRate();if(!0===this._checkIfNeedToExpandKnownPage(r,o))return await this._expandPagedSet(r,o,0,0,l),this._getFeatures(r,s,a,l);let u=0;for(let e=r._lastFetchedIndex;e<r._known.length&&(u++,u<=a&&(r._lastFetchedIndex+=1),!(void 0===this._featureCache[r._known[e]]&&(r._known[e]!==s&&n.push(r._known[e]),n.length>=o)));e++);if(0===n.length)return"success";r=new i([],n,r._ordered,null);const h=Math.min(n.length,a);await(this._parent?._getFeatures(r,-1,h,l)),this._checkCancelled(l);const c=[];for(let e=0;e<h;e++){const t=this._parent?._featureFromCache(n[e]);void 0!==t&&c.push({geometry:t.geometry,attributes:t.attributes,id:n[e]})}for(const i of c){const r=[];for(const e of this.adaptedFields)r[e.field.name]=e.extractValue(i);this._featureCache[i.id]=new e({attributes:r,geometry:t(i.geometry)})}return"success"}async _fetchAndRefineFeatures(){throw new r(s.NeverReach)}async _getFilteredSet(e,t,r,s,a){let l=!1;const n=this._reformulateWithoutAdaptions(r);l=n.cannot,r=n.where;let o=!1;if(null!==s){o=!0;const e=[];for(const t of this.adaptedFields)if(!(t instanceof k)&&!0===s.scanForField(t.field.name)){if(!(t instanceof b)){s=null,o=!1;break}e.push({field:t.field.name,newfield:t.originalField.name})}s&&e.length>0&&(s=s.replaceFields(e))}null!==r?null!==this._extraFilter&&(r=F(this._extraFilter,r)):r=this._extraFilter,await this._ensureLoaded();const u=await this._parent._getFilteredSet(e,t,r,s,a);let h;return this._checkCancelled(a),h=!0===l?new i(u._candidates.slice().concat(u._known.slice()),[],!0===o&&u._ordered,this._clonePageDefinition(u.pagesDefinition)):new i(u._candidates.slice(),u._known.slice(),!0===o&&u._ordered,this._clonePageDefinition(u.pagesDefinition)),h}_reformulateWithoutAdaptions(e){const t={cannot:!1,where:e};if(null!==e)for(const r of this.adaptedFields)if(!0===W(e,r.field.name)){const s=r.rewriteSql(e,this);if(!0!==s.rewritten){t.cannot=!0,t.where=null;break}t.where=s.where}return t}async _stat(e,t,r,s,a,i,l){let n=!1,o=this._reformulateWithoutAdaptions(t);if(n=o.cannot,t=o.where,o=this._reformulateWithoutAdaptions(a),n=n||o.cannot,null!==(a=o.where)?null!==this._extraFilter&&(a=F(this._extraFilter,a)):a=this._extraFilter,!0===n)return null===a&&""===r&&null===s?this._manualStat(e,t,i,l):{calculated:!1};const u=await this._parent._stat(e,t,r,s,a,i,l);return!1===u.calculated?null===a&&""===r&&null===s?this._manualStat(e,t,i,l):{calculated:!1}:u}async _canDoAggregates(e,t,r,s,a){if(null===this._parent)return!1;for(let n=0;n<e.length;n++)for(const t of this.adaptedFields)if(e[n].toLowerCase()===t.field.name.toLowerCase()&&!(t instanceof k))return!1;const i=[];for(let n=0;n<t.length;n++){const e=t[n];if(null!==e.workingexpr){const t=this._reformulateWithoutAdaptions(e.workingexpr);if(t.cannot)return!1;const r=e.clone();r.workingexpr=t.where,i.push(r)}else i.push(e)}const l=this._reformulateWithoutAdaptions(a);return!l.cannot&&(null!==(a=l.where)?null!==this._extraFilter&&(a=F(this._extraFilter,a)):a=this._extraFilter,this._parent._canDoAggregates(e,i,r,s,a))}async _getAggregatePagesDataSourceDefinition(e,t,a,i,l,n,o){if(null===this._parent)throw new r(s.NeverReach);const u=[];for(let c=0;c<t.length;c++){const e=t[c];if(null!==e.workingexpr){const t=this._reformulateWithoutAdaptions(e.workingexpr);if(t.cannot)throw new r(s.NeverReach);const a=e.clone();a.workingexpr=t.where,u.push(a)}else u.push(e)}const h=this._reformulateWithoutAdaptions(l);if(h.cannot)throw new r(s.NeverReach);return null!==(l=h.where)?null!==this._extraFilter&&(l=F(this._extraFilter,l)):l=this._extraFilter,this._parent._getAggregatePagesDataSourceDefinition(e,u,a,i,l,n,o)}}export{R as AdaptedFeatureSet,I as AdaptedField,b as FieldRename,k as OriginalField,L as SqlExpressionAdapted,B as StringToCodeAdapted};