Skip to content

Commit

Permalink
fix: primitive value issue
Browse files Browse the repository at this point in the history
  • Loading branch information
Soontao committed Jun 20, 2021
1 parent 5c805d7 commit 97b432c
Show file tree
Hide file tree
Showing 7 changed files with 111 additions and 66 deletions.
8 changes: 4 additions & 4 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@
"release": "standard-version --no-verify && git push --follow-tags origin master"
},
"devDependencies": {
"@odata/metadata": "^0.2.2",
"@odata/metadata": "^0.2.4",
"@types/jest": "^26.0.23",
"@types/node": "^14.14.41",
"@typescript-eslint/eslint-plugin": "^4.27.0",
Expand Down
25 changes: 15 additions & 10 deletions src/builder/filter.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import join from '@newdash/newdash/join';
import { ODataDataObject } from './types';
import { Edm } from '@odata/metadata';
import { convertPrimitiveValueToString } from './types';

export enum ExprOperator {
eq = 'eq',
Expand Down Expand Up @@ -47,6 +48,10 @@ class ODataFieldExpr {

private _addExpr(op: ExprOperator, value: any) {

if (value === null) {
this._getFieldExprs().push({ op, value: 'null' })
}

switch (typeof value) {
case 'number': case 'boolean':
this._getFieldExprs().push({ op, value: `${value}` });
Expand All @@ -59,8 +64,8 @@ class ODataFieldExpr {
}
break;
case 'object':
if (value instanceof ODataDataObject) {
this._getFieldExprs().push({ op, value: value.toString() });
if (value instanceof Edm.PrimitiveTypeValue) {
this._getFieldExprs().push({ op, value: convertPrimitiveValueToString(value) });
} else {
throw new Error(`Not support object ${value?.constructor?.name || typeof value} in odata filter eq/ne/gt/ge/ne/nt ...`);
}
Expand All @@ -77,7 +82,7 @@ class ODataFieldExpr {
* equal
* @param value
*/
eq(value: number | string | ODataDataObject): ODataFilter {
eq(value: number | string | Edm.PrimitiveTypeValue): ODataFilter {
this._addExpr(ExprOperator.eq, value);
return this._filter;
}
Expand All @@ -86,7 +91,7 @@ class ODataFieldExpr {
* not equal
* @param value
*/
ne(value: number | string | ODataDataObject): ODataFilter {
ne(value: number | string | Edm.PrimitiveTypeValue): ODataFilter {
this._addExpr(ExprOperator.ne, value);
return this._filter;
}
Expand All @@ -105,7 +110,7 @@ class ODataFieldExpr {
* greater or equal
* @param value
*/
ge(value: number | string | ODataDataObject): ODataFilter {
ge(value: number | string | Edm.PrimitiveTypeValue): ODataFilter {
this._addExpr(ExprOperator.ge, value);
return this._filter;
}
Expand All @@ -114,7 +119,7 @@ class ODataFieldExpr {
* greater than
* @param value
*/
gt(value: number | string | ODataDataObject): ODataFilter {
gt(value: number | string | Edm.PrimitiveTypeValue): ODataFilter {
this._addExpr(ExprOperator.gt, value);
return this._filter;
}
Expand All @@ -123,7 +128,7 @@ class ODataFieldExpr {
* less or equal
* @param value
*/
le(value: number | string | ODataDataObject): ODataFilter {
le(value: number | string | Edm.PrimitiveTypeValue): ODataFilter {
this._addExpr(ExprOperator.le, value);
return this._filter;
}
Expand All @@ -132,7 +137,7 @@ class ODataFieldExpr {
* less than
* @param value
*/
lt(value: number | string | ODataDataObject): ODataFilter {
lt(value: number | string | Edm.PrimitiveTypeValue): ODataFilter {
this._addExpr(ExprOperator.lt, value);
return this._filter;
}
Expand All @@ -142,7 +147,7 @@ class ODataFieldExpr {
*
* @param values
*/
in(values: Array<number | string | ODataDataObject> = []): ODataFilter {
in(values: Array<number | string | Edm.PrimitiveTypeValue> = []): ODataFilter {
if (values.length > 0) {
values.forEach((value) => {
this.eq(value);
Expand Down
1 change: 1 addition & 0 deletions src/builder/index.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { ODataFilter } from './filter';
import { ODataParam } from './param';

export { Edm } from "@odata/metadata";
export * from './batch';
export * from './filter';
export * from './param';
Expand Down
111 changes: 65 additions & 46 deletions src/builder/types.ts
Original file line number Diff line number Diff line change
@@ -1,57 +1,76 @@
import { Edm } from "@odata/metadata";

export abstract class ODataDataObject {
abstract toString(): string;
}

export class ODataDateTimeV4 extends ODataDataObject {

private constructor(date: Date) {
super();
this._date = date;
}

static from(date: Date): ODataDateTimeV4;
static from(date: string): ODataDateTimeV4;
static from(date: any): ODataDateTimeV4 {
switch (typeof date) {
case 'string':
return new ODataDateTimeV4(new Date(date));
default:
return new ODataDateTimeV4(date);
}
}

private _date: Date

public toString(): string {
return `${this._date.toISOString()}`;
/**
*
* @param value primitive literal value
* @returns the string representation
*/
export function convertPrimitiveValueToString(value: Edm.PrimitiveTypeValue) {
if (value?.getValue?.() === null) {
return 'null'
}

}

export class ODataDateTimeOffsetV4 extends ODataDataObject {
if (value?.getValue?.() !== undefined) {

private constructor(date: Date) {
super();
this._date = date;
}

static from(date: Date): ODataDateTimeOffsetV4;
static from(date: string): ODataDateTimeOffsetV4;
static from(date: any): ODataDateTimeOffsetV4 {
switch (typeof date) {
case 'string':
return new ODataDateTimeOffsetV4(new Date(date));
switch (value?.getType?.()) {
case Edm.Int16:
case Edm.Int32:
case Edm.Int64:
case Edm.Guid:
case Edm.Double:
case Edm.Decimal:
case Edm.Byte:
case Edm.SByte:
case Edm.Single:
return String(value.getValue())
case Edm.Boolean:
return String(value.getValue())
case Edm.Binary:
let vB = value.getValue()
if (vB instanceof Buffer) {
return `binary'${vB.toString("base64")}'`
}
return String(vB)
case Edm.String:
return `'${value.getValue()}'`
case Edm.Duration:
// TODO integrate with some other duration lib
return value.getValue();
case Edm.DateTimeOffset:
let v1 = value.getValue()
if (typeof v1 === 'string') {
v1 = new Date(v1)
}
return v1.toISOString()
case Edm.Date:
const v2 = value.getValue()
if (v2 instanceof Date) {
return `${v2.getFullYear()}-${v2.getMonth() + 1}-${v2.getDate()}`
}
return v2
case Edm.Geography:
case Edm.GeographyPoint:
case Edm.GeographyLineString:
case Edm.GeographyPolygon:
case Edm.GeographyMultiPoint:
case Edm.GeographyMultiLineString:
case Edm.GeographyMultiPolygon:
case Edm.GeographyCollection:
case Edm.Geometry:
case Edm.GeometryPoint:
case Edm.GeometryLineString:
case Edm.GeometryPolygon:
case Edm.GeometryMultiPoint:
case Edm.GeometryMultiLineString:
case Edm.GeometryMultiPolygon:
case Edm.GeometryCollection:
return String(value.getValue())
default:
return new ODataDateTimeOffsetV4(date);
throw new TypeError(`not support type '${value.getType()}'`)
}
}

throw new Error("'undefined' value provided")

private _date: Date

public toString(): string {
return `${this._date.toISOString()}`;
}

}
24 changes: 22 additions & 2 deletions test/builder/filter.test.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,11 @@
import { filter, ODataFilter } from '../../src';
import { Edm, filter, ODataFilter } from '../../src';

describe('OData Query Builder - Filter Test Suite', () => {

it('should support filter by value/name', () => {

expect(ODataFilter.New().field('A').eq('a').toString()).toBe("A eq 'a'");
expect(ODataFilter.New().field('A').eq(Edm.String.createValue("a")).toString()).toBe("A eq 'a'");
expect(ODataFilter.New().field('A').eq(1).toString()).toBe('A eq 1');

});
Expand All @@ -15,10 +16,29 @@ describe('OData Query Builder - Filter Test Suite', () => {
B: string;
}
expect(ODataFilter.New<Type>({ A: 1, B: '2' }).toString()).toBe("A eq 1 and B eq '2'");

expect(ODataFilter.New<any>({
A: Edm.Int16.createValue(12),
B: Edm.String.createValue('12')
}).toString()).toBe("A eq 12 and B eq '12'");
});

it('should support filter alias', () => {
expect(filter({A:1}).build()).toBe('A eq 1');
expect(filter({ A: 1 }).build()).toBe('A eq 1');
});

it('should support filter guid', () => {
expect(
filter()
.field("A")
.eq(Edm.Guid.createValue("253f842d-d739-41b8-ac8c-139ac7a9dd14"))
.build()
).toBe("A eq 253f842d-d739-41b8-ac8c-139ac7a9dd14")

expect(
filter({ A: Edm.Guid.createValue("253f842d-d739-41b8-ac8c-139ac7a9dd14") })
.build()
).toBe("A eq 253f842d-d739-41b8-ac8c-139ac7a9dd14")
});

});
6 changes: 3 additions & 3 deletions test/filter.spec.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { get } from '@newdash/newdash';
import { Edm } from "@odata/metadata";
import { defaultParser, ODataDateTimeOffsetV4, ODataDateTimeV4, ODataFilter } from '../src';
import { defaultParser, ODataFilter } from '../src';


describe('Filter Test Suite', () => {
Expand Down Expand Up @@ -29,8 +29,8 @@ describe('Filter Test Suite', () => {
.field('F').between(1, 3, true)
.field('E').in(['a', 'c', 'd'])
.field('year(Date)').eq(2010)
.field('Date2').gt(ODataDateTimeOffsetV4.from('2020-07-30T03:16:27.023Z'))
.field('Date3').lt(ODataDateTimeV4.from(new Date()))
.field('Date2').gt(Edm.DateTimeOffset.createValue('2020-07-30T03:16:27.023Z'))
.field('Date3').lt(Edm.DateTimeOffset.createValue(new Date()))
.toString();

defaultParser.filter(sFilter);
Expand Down

0 comments on commit 97b432c

Please sign in to comment.