Skip to content

Commit c565ead

Browse files
authored
Merge pull request #10 from upstash/dx-661-add-ts-definition-tests
test: add definition tests for metadata commands
2 parents 2bb5703 + 464325e commit c565ead

File tree

8 files changed

+226
-26
lines changed

8 files changed

+226
-26
lines changed

bun.lockb

20.5 KB
Binary file not shown.

package.json

+27-26
Original file line numberDiff line numberDiff line change
@@ -1,41 +1,42 @@
11
{
22
"name": "@upstash/vector",
3-
"description": "An HTTP/REST based Vector DB client built on top of Upstash REST API.",
4-
"module": "./dist/index.mjs",
5-
"main": "./dist/index.js",
6-
"types": "./dist/index.d.ts",
73
"version": "v0.1.0-alpha-9",
4+
"author": "Oguzhan Olguncu <[email protected]>",
5+
"repository": {
6+
"type": "git",
7+
"url": "https://github.com/upstash/vector-js"
8+
},
9+
"main": "./dist/index.js",
10+
"module": "./dist/index.mjs",
11+
"devDependencies": {
12+
"@biomejs/biome": "^1.4.1",
13+
"@commitlint/cli": "^18.6.0",
14+
"@commitlint/config-conventional": "^18.6.0",
15+
"bun-types": "latest",
16+
"husky": "^8.0.3",
17+
"tsup": "latest",
18+
"typescript": "^5.0.0",
19+
"vitest": "^1.2.2"
20+
},
21+
"bugs": {
22+
"url": "https://github.com/upstash/vector/issues"
23+
},
24+
"description": "An HTTP/REST based Vector DB client built on top of Upstash REST API.",
25+
"files": [
26+
"dist"
27+
],
28+
"homepage": "https://upstash.com/vector",
829
"keywords": [
930
"vector",
1031
"upstash",
1132
"db"
1233
],
13-
"author": "Oguzhan Olguncu <[email protected]>",
1434
"license": "MIT",
15-
"files": [
16-
"dist"
17-
],
18-
"bugs": {
19-
"url": "https://github.com/upstash/vector/issues"
20-
},
2135
"scripts": {
22-
"test": "bun test src --coverage --bail --coverageSkipTestFiles=[test-utils.ts]",
36+
"test": "bun test src --coverage --bail --coverageSkipTestFiles=[test-utils.ts] && vitest run --typecheck",
2337
"fmt": "bunx biome check --apply ./src",
2438
"build": "tsup",
2539
"prepare": "husky install"
2640
},
27-
"devDependencies": {
28-
"typescript": "^5.0.0",
29-
"@biomejs/biome": "^1.4.1",
30-
"@commitlint/cli": "^18.6.0",
31-
"@commitlint/config-conventional": "^18.6.0",
32-
"bun-types": "latest",
33-
"husky": "^8.0.3",
34-
"tsup": "latest"
35-
},
36-
"repository": {
37-
"type": "git",
38-
"url": "https://github.com/upstash/vector-js"
39-
},
40-
"homepage": "https://upstash.com/vector"
41+
"types": "./dist/index.d.ts"
4142
}
+46
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
import { expectTypeOf, test } from "vitest";
2+
import { Index } from "../../../../index";
3+
4+
type Metadata = { genre: string; year: number };
5+
6+
test("case 1: no metadata is provided, any object should be expected", () => {
7+
const index = new Index();
8+
9+
type RetrievedFetchVector = Awaited<ReturnType<typeof index.fetch>>[number];
10+
11+
type RetrievedMetadata = NonNullable<NonNullable<RetrievedFetchVector>["metadata"]>;
12+
13+
expectTypeOf<RetrievedMetadata>().toEqualTypeOf<Record<string, unknown>>();
14+
});
15+
16+
test("case 2: index-level metadata is provided, index-level metadata should be expected", () => {
17+
const index = new Index<Metadata>();
18+
19+
type RetrievedFetchVector = Awaited<ReturnType<typeof index.fetch<Metadata>>>[number];
20+
21+
type RetrievedMetadata = NonNullable<NonNullable<RetrievedFetchVector>["metadata"]>;
22+
23+
expectTypeOf<RetrievedMetadata>().toEqualTypeOf<Metadata>();
24+
});
25+
26+
test("case 3: index-level and command-level metadata are provided, command-level metadata should be expected", () => {
27+
const index = new Index<Metadata>();
28+
29+
type OverrideMetadata = { director: string };
30+
31+
type RetrievedFetchVector = Awaited<ReturnType<typeof index.fetch<OverrideMetadata>>>[number];
32+
33+
type RetrievedMetadata = NonNullable<NonNullable<RetrievedFetchVector>["metadata"]>;
34+
35+
expectTypeOf<RetrievedMetadata>().toEqualTypeOf<OverrideMetadata>();
36+
});
37+
38+
test("case 4: command-level metadata is provided, command-level metadata should be expected", () => {
39+
const index = new Index();
40+
41+
type RetrievedFetchVector = Awaited<ReturnType<typeof index.fetch<Metadata>>>[number];
42+
43+
type RetrievedMetadata = NonNullable<NonNullable<RetrievedFetchVector>["metadata"]>;
44+
45+
expectTypeOf<RetrievedMetadata>().toEqualTypeOf<Metadata>();
46+
});
+46
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
import { expectTypeOf, test } from "vitest";
2+
import { Index } from "../../../../index";
3+
4+
type Metadata = { genre: string; year: number };
5+
6+
test("case 1: no metadata is provided, any object should be expected", () => {
7+
const index = new Index();
8+
9+
type RetrievedQueryVector = Awaited<ReturnType<typeof index.query>>[number];
10+
11+
type RetrievedMetadata = NonNullable<NonNullable<RetrievedQueryVector>["metadata"]>;
12+
13+
expectTypeOf<RetrievedMetadata>().toEqualTypeOf<Record<string, unknown>>();
14+
});
15+
16+
test("case 2: index-level metadata is provided, index-level metadata should be expected", () => {
17+
const index = new Index<Metadata>();
18+
19+
type RetrievedQueryVector = Awaited<ReturnType<typeof index.query<Metadata>>>[number];
20+
21+
type RetrievedMetadata = NonNullable<NonNullable<RetrievedQueryVector>["metadata"]>;
22+
23+
expectTypeOf<RetrievedMetadata>().toEqualTypeOf<Metadata>();
24+
});
25+
26+
test("case 3: index-level and command-level metadata are provided, command-level metadata should be expected", () => {
27+
const index = new Index<Metadata>();
28+
29+
type OverrideMetadata = { director: string };
30+
31+
type RetrievedQueryVector = Awaited<ReturnType<typeof index.query<OverrideMetadata>>>[number];
32+
33+
type RetrievedMetadata = NonNullable<NonNullable<RetrievedQueryVector>["metadata"]>;
34+
35+
expectTypeOf<RetrievedMetadata>().toEqualTypeOf<OverrideMetadata>();
36+
});
37+
38+
test("case 4: command-level metadata is provided, command-level metadata should be expected", () => {
39+
const index = new Index();
40+
41+
type RetrievedQueryVector = Awaited<ReturnType<typeof index.query<Metadata>>>[number];
42+
43+
type RetrievedMetadata = NonNullable<NonNullable<RetrievedQueryVector>["metadata"]>;
44+
45+
expectTypeOf<RetrievedMetadata>().toEqualTypeOf<Metadata>();
46+
});
+48
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
import { expectTypeOf, test } from "vitest";
2+
import { Index } from "../../../../index";
3+
4+
type Metadata = { genre: string; year: number };
5+
6+
test("case 1: no metadata is provided, any object should be expected", () => {
7+
const index = new Index();
8+
9+
type RetrievedRangeVector = Awaited<ReturnType<typeof index.range>>["vectors"][number];
10+
11+
type RetrievedMetadata = NonNullable<NonNullable<RetrievedRangeVector>["metadata"]>;
12+
13+
expectTypeOf<RetrievedMetadata>().toEqualTypeOf<Record<string, unknown>>();
14+
});
15+
16+
test("case 2: index-level metadata is provided, index-level metadata should be expected", () => {
17+
const index = new Index<Metadata>();
18+
19+
type RetrievedRangeVector = Awaited<ReturnType<typeof index.range<Metadata>>>["vectors"][number];
20+
21+
type RetrievedMetadata = NonNullable<NonNullable<RetrievedRangeVector>["metadata"]>;
22+
23+
expectTypeOf<RetrievedMetadata>().toEqualTypeOf<Metadata>();
24+
});
25+
26+
test("case 3: index-level and command-level metadata are provided, command-level metadata should be expected", () => {
27+
const index = new Index<Metadata>();
28+
29+
type OverrideMetadata = { director: string };
30+
31+
type RetrievedRangeVector = Awaited<
32+
ReturnType<typeof index.range<OverrideMetadata>>
33+
>["vectors"][number];
34+
35+
type RetrievedMetadata = NonNullable<NonNullable<RetrievedRangeVector>["metadata"]>;
36+
37+
expectTypeOf<RetrievedMetadata>().toEqualTypeOf<OverrideMetadata>();
38+
});
39+
40+
test("case 4: command-level metadata is provided, command-level metadata should be expected", () => {
41+
const index = new Index();
42+
43+
type RetrievedRangeVector = Awaited<ReturnType<typeof index.range<Metadata>>>["vectors"][number];
44+
45+
type RetrievedMetadata = NonNullable<NonNullable<RetrievedRangeVector>["metadata"]>;
46+
47+
expectTypeOf<RetrievedMetadata>().toEqualTypeOf<Metadata>();
48+
});
+46
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
import { NonArrayType } from "@utils/test-utils";
2+
import { expectTypeOf, test } from "vitest";
3+
import { Index } from "../../../../index";
4+
5+
type Metadata = { genre: string; year: number };
6+
7+
test("case 1: no metadata is provided, any object should be expected", () => {
8+
const index = new Index();
9+
10+
// ideally we would not have to pass the same generic again but infer from the index signature
11+
type ExpectedParameters = Parameters<typeof index.upsert>["0"];
12+
type ExpectedMetadata = NonNullable<NonArrayType<ExpectedParameters>["metadata"]>;
13+
14+
expectTypeOf<ExpectedMetadata>().toEqualTypeOf<Record<string, unknown>>();
15+
});
16+
17+
test("case 2: index-level metadata is provided, index-level metadata should be expected", () => {
18+
const index = new Index<Metadata>();
19+
20+
// ideally we would not have to pass the same generic again but infer from the index signature instead
21+
type ExpectedParameters = Parameters<typeof index.upsert<Metadata>>["0"];
22+
type ExpectedMetadata = NonNullable<NonArrayType<ExpectedParameters>["metadata"]>;
23+
24+
expectTypeOf<ExpectedMetadata>().toEqualTypeOf<Metadata>();
25+
});
26+
27+
test("case 3: index-level metadata is provided and command-level metadata is provided, command-level metadata should be expected", () => {
28+
const index = new Index<Metadata>();
29+
30+
type OverrideMetadata = { director: string };
31+
32+
type ExpectedParameters = Parameters<typeof index.upsert<OverrideMetadata>>["0"];
33+
type ExpectedMetadata = NonNullable<NonNullable<NonArrayType<ExpectedParameters>>["metadata"]>;
34+
35+
expectTypeOf<ExpectedMetadata>().toEqualTypeOf<OverrideMetadata>();
36+
});
37+
38+
test("case 4: command-level metadata is provided, command-level metadata should be expected", () => {
39+
const index = new Index();
40+
41+
type ExpectedParameters = Parameters<typeof index.upsert<Metadata>>["0"];
42+
43+
type ExpectedMetadata = NonNullable<NonNullable<NonArrayType<ExpectedParameters>>["metadata"]>;
44+
45+
expectTypeOf<ExpectedMetadata>().toEqualTypeOf<Metadata>();
46+
});

src/utils/test-utils.ts

+2
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
11
import { ResetCommand } from "../commands/client/reset";
22
import { HttpClient, RetryConfig } from "../http";
33

4+
export type NonArrayType<T> = T extends Array<infer U> ? U : T;
5+
46
export const newHttpClient = (retry?: RetryConfig | undefined) => {
57
const url = process.env.UPSTASH_VECTOR_REST_URL;
68
if (!url) {

vitest.config.ts

+11
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
/// <reference types="vitest" />
2+
import { defineConfig } from "vite"
3+
4+
export default defineConfig({
5+
test: {
6+
typecheck: {
7+
include: ["**/*.test-d.ts"],
8+
only: true,
9+
},
10+
},
11+
})

0 commit comments

Comments
 (0)