diff --git a/types/parse/index.d.ts b/types/parse/index.d.ts index c57e21b059..68ae023efb 100644 --- a/types/parse/index.d.ts +++ b/types/parse/index.d.ts @@ -1,4 +1,4 @@ -// Type definitions for parse 2.10 +// Type definitions for parse 2.12 // Project: https://parseplatform.org/ // Definitions by: Ullisen Media Group // David Poetzsch-Heffter @@ -22,6 +22,7 @@ // Patrick O'Sullivan // Jerome De Leon // Kent Robin Haugen +// Asen Lekov // Definitions: https://github.com/DefinitelyTyped/DefinitelyTyped // TypeScript Version: 3.5 @@ -293,10 +294,19 @@ namespace Parse { * @returns Promise that is resolved with base64 data */ getData(): Promise; + url(options?: { forceSecure?: boolean }): string; + metadata(): Record; + tags(): Record; name(): string; save(options?: SuccessFailureOptions): Promise; + cancel(): void; + destroy(): Promise; toJSON(): { __type: string, name: string, url: string }; - url(options?: { forceSecure: boolean }): string; + equals(other: File): boolean; + setMetadata(metadata: Record): void; + addMetadata(key: string, value: any): void; + setTags(tags: Record): void; + addTag(key: string, value: any): void; } /** @@ -422,6 +432,7 @@ namespace Parse { getACL(): ACL | undefined; has(attr: Extract): boolean; increment(attr: Extract, amount?: number): this | false; + decrement(attr: Extract, amount?: number): this | false; initialize(): void; isDataAvailable(): boolean; isNew(): boolean; @@ -657,15 +668,24 @@ namespace Parse { X extends Extract>(key: K, queryKey: X, query: Query): this; doesNotMatchQuery(key: K, query: Query): this; distinct(key: K): Promise; - each(callback: (obj: T) => PromiseLike | void, options?: Query.EachOptions): Promise; + eachBatch(callback: (objs: T[]) => PromiseLike | void, options?: Query.BatchOptions): Promise; + each(callback: (obj: T) => PromiseLike | void, options?: Query.BatchOptions): Promise; + hint(value: string | object): this; + explain(explain: boolean): this; + map(callback: (currentObject: T, index: number, query: Query) => PromiseLike | U, options?: Query.BatchOptions): Promise; + reduce(callback: (accumulator: T, currentObject: T, index: number) => PromiseLike | T, initialValue?: undefined, options?: Query.BatchOptions): Promise; + reduce(callback: (accumulator: U, currentObject: T, index: number) => PromiseLike | U, initialValue: U, options?: Query.BatchOptions): Promise; + filter(callback: (currentObject: T, index: number, query: Query) => PromiseLike | boolean, options?: Query.BatchOptions): Promise; endsWith(key: K, suffix: string): this; equalTo(key: K, value: T['attributes'][K] | (T['attributes'][K] extends Object ? Pointer : never)): this; exists(key: K): this; find(options?: Query.FindOptions): Promise; first(options?: Query.FirstOptions): Promise; - fromLocalDatastore(): void; - fromPin(): void; - fromPinWithName(name: string): void; + fromNetwork(): this; + fromLocalDatastore(): this; + fromPin(): this; + fromPinWithName(name: string): this; + cancel(): this; fullText(key: K, value: string, options?: Query.FullTextOptions): this; get(objectId: string, options?: Query.GetOptions): Promise; greaterThan(key: K, value: T['attributes'][K]): this; @@ -720,6 +740,10 @@ namespace Parse { caseSensitive?: boolean; diacriticSensitive?: boolean; } + + interface BatchOptions extends FullOptions { + batchSize?: number; + } } /** @@ -1109,6 +1133,12 @@ namespace Parse { context: object; } + interface FileTriggerRequest extends TriggerRequest { + file: File; + fileSize: number; + contentLength: number; + } + // Read preference describes how MongoDB driver route read operations to the members of a replica set. enum ReadPreferenceOption { Primary = 'PRIMARY', @@ -1138,7 +1168,16 @@ namespace Parse { func?: (request: BeforeFindRequest) => Promise | Promise | Query | void ): void; function afterFind(arg1: any, func?: (request: AfterFindRequest) => any): void; - function beforeLogin(func?: (request: TriggerRequest) => any): void; + + function beforeLogin(func?: (request: TriggerRequest) => PromiseLike | void): void; + function afterLogin(func?: (request: TriggerRequest) => PromiseLike | void): void; + function afterLogout(func?: (request: TriggerRequest) => PromiseLike | void): void; + + function beforeSaveFile(func?: (request: FileTriggerRequest) => PromiseLike | void): void; + function afterSaveFile(func?: (request: FileTriggerRequest) => PromiseLike | void): void; + function beforeDeleteFile(func?: (request: FileTriggerRequest) => PromiseLike | void): void; + function afterDeleteFile(func?: (request: FileTriggerRequest) => PromiseLike | void): void; + function define(name: string, func: (request: FunctionRequest) => any): void; function define any>( name: string, diff --git a/types/parse/parse-tests.ts b/types/parse/parse-tests.ts index ae07b69fbb..14cf85e195 100644 --- a/types/parse/parse-tests.ts +++ b/types/parse/parse-tests.ts @@ -99,6 +99,10 @@ function test_query() { query.notEqualTo('playerName', 'Michael Yabuti'); query.fullText('playerName', 'dan', { language: 'en', caseSensitive: false, diacriticSensitive: true }); query.greaterThan('playerAge', 18); + query.eachBatch((objs) => Promise.resolve(), {batchSize: 10}); + query.each((score) => Promise.resolve()); + query.hint('_id_'); + query.explain(true); query.limit(10); query.skip(10); @@ -181,6 +185,12 @@ async function test_query_promise() { } catch (error) { // noop } + + await getQuery.map((score, index) => score.increment("score", index)); + await getQuery.reduce((accum, score, index) => accum + score.get("score"), 0); + await getQuery.reduce((accum, score, index) => accum + score.get("score"), 0, { batchSize: 200 }); + await getQuery.filter((scores) => scores.get('score') > 0); + await getQuery.filter((scores) => scores.get('score') > 0, { batchSize: 10 }); } async function test_live_query() { @@ -242,6 +252,7 @@ function test_file() { file = new Parse.File('myfile.zzz', new Blob(), 'image/png'); const src = file.url(); + const secure = file.url({forceSecure: true}); file.save().then( () => { @@ -255,8 +266,25 @@ function test_file() { Parse.Cloud.httpRequest({ url: file.url() }).then((response: Parse.Cloud.HttpResponse) => { // result }); - // TODO: Check + + file.cancel(); + file.destroy(); +} + +function test_file_tags_and_metadata() { + const base64 = 'V29ya2luZyBhdCBQYXJzZSBpcyBncmVhdCE='; + const file = new Parse.File('myfile.txt', { base64 }); + file.setTags({ownerId: 42, status: "okay"}); + file.addTag('labes', ['one', 'two', 'three']); + file.setMetadata({contentType: 'plain/text', contentLength: 579}); + file.addMetadata('author', 'John Doe'); + + const tags = file.tags(); + const ownerId = tags['ownerId']; + + const metadata = file.metadata(); + const contentType = metadata['contentType']; } function test_analytics() { @@ -562,7 +590,28 @@ async function test_cloud_functions() { }); Parse.Cloud.beforeLogin((request: Parse.Cloud.TriggerRequest) => { - return 'Some result'; + return Promise.resolve(); + }); + + Parse.Cloud.afterLogin((request: Parse.Cloud.TriggerRequest) => { + return Promise.resolve(); + }); + + Parse.Cloud.afterLogout((request: Parse.Cloud.TriggerRequest) => { + return Promise.resolve(); + }); + + Parse.Cloud.beforeSaveFile((request: Parse.Cloud.FileTriggerRequest) => { + return Promise.resolve(new Parse.File("myFile.txt", {base64: ''})); + }); + + Parse.Cloud.beforeSaveFile((request: Parse.Cloud.FileTriggerRequest) => { + }); + + Parse.Cloud.beforeDeleteFile((request: Parse.Cloud.FileTriggerRequest) => { + }); + + Parse.Cloud.afterDeleteFile((request: Parse.Cloud.FileTriggerRequest) => { }); Parse.Cloud.define('AFunc', (request: Parse.Cloud.FunctionRequest) => { @@ -764,6 +813,23 @@ async function test_local_datastore() { Parse.setLocalDatastoreController({}); } +async function test_from_network() { + const obj = new Parse.Object('TestObject'); + await obj.save(); + + const query = new Parse.Query('TestObject'); + query.fromNetwork(); +} + +async function test_cancel_query() { + const obj = new Parse.Object('TestObject'); + await obj.save(); + + const query = new Parse.Query('TestObject'); + query.fromNetwork().find(); + query.cancel(); +} + type FieldType = string | number | boolean | Date | Parse.File | Parse.GeoPoint | any[] | object | Parse.Pointer | Parse.Polygon | Parse.Relation; async function test_schema( anyField: FieldType, @@ -1093,6 +1159,26 @@ function testObject() { objTyped.increment('other'); } + function testDecrement(objUntyped: Parse.Object, objTyped: Parse.Object<{ example: number }>) { + // $ExpectType false | Object + objUntyped.decrement('whatever'); + + // $ExpectType false | Object + objUntyped.decrement('whatever', 10); + + // $ExpectType false | Object<{ example: number; }> + objTyped.decrement('example'); + + // $ExpectType false | Object<{ example: number; }> + objTyped.decrement('example', 20); + + // $ExpectError + objTyped.decrement('example', true); + + // $ExpectError + objTyped.decrement('other'); + } + function testNewInstance(objUntyped: Parse.Object, objTyped: Parse.Object<{ example: number }>) { // $ExpectType Object objUntyped.newInstance(); diff --git a/types/parse/ts3.7/index.d.ts b/types/parse/ts3.7/index.d.ts index 588ecb17aa..fba8d7facc 100644 --- a/types/parse/ts3.7/index.d.ts +++ b/types/parse/ts3.7/index.d.ts @@ -266,10 +266,19 @@ namespace Parse { * @returns Promise that is resolved with base64 data */ getData(): Promise; + url(options?: { forceSecure?: boolean }): string; + metadata(): Record; + tags(): Record; name(): string; save(options?: SuccessFailureOptions): Promise; + cancel(): void; + destroy(): Promise; toJSON(): { __type: string, name: string, url: string }; - url(options?: { forceSecure: boolean }): string; + equals(other: File): boolean; + setMetadata(metadata: Record): void; + addMetadata(key: string, value: any): void; + setTags(tags: Record): void; + addTag(key: string, value: any): void; } /** @@ -395,6 +404,7 @@ namespace Parse { getACL(): ACL | undefined; has(attr: Extract): boolean; increment(attr: Extract, amount?: number): this | false; + decrement(attr: Extract, amount?: number): this | false; initialize(): void; isDataAvailable(): boolean; isNew(): boolean; @@ -630,15 +640,24 @@ namespace Parse { X extends Extract>(key: K, queryKey: X, query: Query): this; doesNotMatchQuery(key: K, query: Query): this; distinct(key: K): Promise; - each(callback: (obj: T) => PromiseLike | void, options?: Query.EachOptions): Promise; + eachBatch(callback: (objs: T[]) => PromiseLike | void, options?: Query.BatchOptions): Promise; + each(callback: (obj: T) => PromiseLike | void, options?: Query.BatchOptions): Promise; + hint(value: string | object): this; + explain(explain: boolean): this; + map(callback: (currentObject: T, index: number, query: Query) => PromiseLike | U, options?: Query.BatchOptions): Promise; + reduce(callback: (accumulator: T, currentObject: T, index: number) => PromiseLike | T, initialValue?: undefined, options?: Query.BatchOptions): Promise; + reduce(callback: (accumulator: U, currentObject: T, index: number) => PromiseLike | U, initialValue: U, options?: Query.BatchOptions): Promise; + filter(callback: (currentObject: T, index: number, query: Query) => PromiseLike | boolean, options?: Query.BatchOptions): Promise; endsWith(key: K, suffix: string): this; equalTo(key: K, value: T['attributes'][K] | (T['attributes'][K] extends Object ? Pointer : never)): this; exists(key: K): this; find(options?: Query.FindOptions): Promise; first(options?: Query.FirstOptions): Promise; - fromLocalDatastore(): void; - fromPin(): void; - fromPinWithName(name: string): void; + fromNetwork(): this; + fromLocalDatastore(): this; + fromPin(): this; + fromPinWithName(name: string): this; + cancel(): this; fullText(key: K, value: string, options?: Query.FullTextOptions): this; get(objectId: string, options?: Query.GetOptions): Promise; greaterThan(key: K, value: T['attributes'][K]): this; @@ -693,6 +712,10 @@ namespace Parse { caseSensitive?: boolean; diacriticSensitive?: boolean; } + + interface BatchOptions extends FullOptions { + batchSize?: number; + } } /** @@ -1081,6 +1104,12 @@ namespace Parse { context: object; } + interface FileTriggerRequest extends TriggerRequest { + file: File; + fileSize: number; + contentLength: number; + } + // Read preference describes how MongoDB driver route read operations to the members of a replica set. enum ReadPreferenceOption { Primary = 'PRIMARY', @@ -1110,7 +1139,16 @@ namespace Parse { func?: (request: BeforeFindRequest) => Promise | Promise | Query | void ): void; function afterFind(arg1: any, func?: (request: AfterFindRequest) => any): void; - function beforeLogin(func?: (request: TriggerRequest) => any): void; + + function beforeLogin(func?: (request: TriggerRequest) => PromiseLike | void): void; + function afterLogin(func?: (request: TriggerRequest) => PromiseLike | void): void; + function afterLogout(func?: (request: TriggerRequest) => PromiseLike | void): void; + + function beforeSaveFile(func?: (request: FileTriggerRequest) => PromiseLike | void): void; + function afterSaveFile(func?: (request: FileTriggerRequest) => PromiseLike | void): void; + function beforeDeleteFile(func?: (request: FileTriggerRequest) => PromiseLike | void): void; + function afterDeleteFile(func?: (request: FileTriggerRequest) => PromiseLike | void): void; + function define(name: string, func: (request: FunctionRequest) => any): void; function define any>( name: string, diff --git a/types/parse/ts3.7/parse-tests.ts b/types/parse/ts3.7/parse-tests.ts index e581318a48..f2fdcbac92 100644 --- a/types/parse/ts3.7/parse-tests.ts +++ b/types/parse/ts3.7/parse-tests.ts @@ -99,6 +99,10 @@ function test_query() { query.notEqualTo('playerName', 'Michael Yabuti'); query.fullText('playerName', 'dan', { language: 'en', caseSensitive: false, diacriticSensitive: true }); query.greaterThan('playerAge', 18); + query.eachBatch((objs) => Promise.resolve(), {batchSize: 10}); + query.each((score) => Promise.resolve()); + query.hint('_id_'); + query.explain(true); query.limit(10); query.skip(10); @@ -181,6 +185,12 @@ async function test_query_promise() { } catch (error) { // noop } + + await getQuery.map((score, index) => score.increment("score", index)); + await getQuery.reduce((accum, score, index) => accum += score.get("score"), 0); + await getQuery.reduce((accum, score, index) => accum += score.get("score"), 0, { batchSize: 200 }); + await getQuery.filter((scores) => scores.get('score') > 0); + await getQuery.filter((scores) => scores.get('score') > 0, { batchSize: 10 }); } async function test_live_query() { @@ -242,6 +252,7 @@ function test_file() { file = new Parse.File('myfile.zzz', new Blob(), 'image/png'); const src = file.url(); + const secure = file.url({forceSecure: true}); file.save().then( () => { @@ -257,6 +268,24 @@ function test_file() { }); // TODO: Check + + file.cancel(); + file.destroy(); +} + +function test_file_tags_and_metadata() { + const base64 = 'V29ya2luZyBhdCBQYXJzZSBpcyBncmVhdCE='; + const file = new Parse.File('myfile.txt', { base64 }); + file.setTags({ownerId: 42, status: "okay"}); + file.addTag('labes', ['one', 'two', 'three']); + file.setMetadata({contentType: 'plain/text', contentLength: 579}); + file.addMetadata('author', 'John Doe'); + + const tags = file.tags(); + const ownerId = tags['ownerId']; + + const metadata = file.metadata(); + const contentType = metadata['contentType']; } function test_analytics() { @@ -562,7 +591,28 @@ async function test_cloud_functions() { }); Parse.Cloud.beforeLogin((request: Parse.Cloud.TriggerRequest) => { - return 'Some result'; + return Promise.resolve(); + }); + + Parse.Cloud.afterLogin((request: Parse.Cloud.TriggerRequest) => { + return Promise.resolve(); + }); + + Parse.Cloud.afterLogout((request: Parse.Cloud.TriggerRequest) => { + return Promise.resolve(); + }); + + Parse.Cloud.beforeSaveFile((request: Parse.Cloud.FileTriggerRequest) => { + return Promise.resolve(new Parse.File("myFile.txt", {base64: ''})); + }); + + Parse.Cloud.beforeSaveFile((request: Parse.Cloud.FileTriggerRequest) => { + }); + + Parse.Cloud.beforeDeleteFile((request: Parse.Cloud.FileTriggerRequest) => { + }); + + Parse.Cloud.afterDeleteFile((request: Parse.Cloud.FileTriggerRequest) => { }); Parse.Cloud.define('AFunc', (request: Parse.Cloud.FunctionRequest) => { @@ -764,6 +814,23 @@ async function test_local_datastore() { Parse.setLocalDatastoreController({}); } +async function test_from_network() { + const obj = new Parse.Object('TestObject'); + await obj.save(); + + const query = new Parse.Query('TestObject'); + query.fromNetwork(); +} + +async function test_cancel_query() { + const obj = new Parse.Object('TestObject'); + await obj.save(); + + const query = new Parse.Query('TestObject'); + query.fromNetwork().find(); + query.cancel(); +} + type FieldType = string | number | boolean | Date | Parse.File | Parse.GeoPoint | any[] | object | Parse.Pointer | Parse.Polygon | Parse.Relation; async function test_schema( anyField: FieldType, @@ -1093,6 +1160,26 @@ function testObject() { objTyped.increment('other'); } + function testDecrement(objUntyped: Parse.Object, objTyped: Parse.Object<{ example: number }>) { + // $ExpectType false | Object + objUntyped.decrement('whatever'); + + // $ExpectType false | Object + objUntyped.decrement('whatever', 10); + + // $ExpectType false | Object<{ example: number; }> + objTyped.decrement('example'); + + // $ExpectType false | Object<{ example: number; }> + objTyped.decrement('example', 20); + + // $ExpectError + objTyped.decrement('example', true); + + // $ExpectError + objTyped.decrement('other'); + } + function testNewInstance(objUntyped: Parse.Object, objTyped: Parse.Object<{ example: number }>) { // $ExpectType Object objUntyped.newInstance();