Skip to content

Commit

Permalink
feat: kv runtime (#797)
Browse files Browse the repository at this point in the history
#### Migration notes

...

- [x] The change comes with new or modified tests
- [x] End-user documentation is updated to reflect the change
- [ ] Hard-to-understand functions have explanatory comments
  • Loading branch information
j03-dev authored Aug 13, 2024
1 parent 1e76c6f commit 54da279
Show file tree
Hide file tree
Showing 22 changed files with 1,080 additions and 4 deletions.
2 changes: 2 additions & 0 deletions examples/metatype.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -151,9 +151,11 @@ typegraphs:
exclude:
- "**/*"
- "typegraphs/temporal.py"
- "typegraphs/kv.py"
typescript:
exclude:
- "typegraphs/temporal.ts"
- "typegraphs/kv.ts"
include:
- "typegraphs/*.ts"
javascript:
Expand Down
24 changes: 24 additions & 0 deletions examples/typegraphs/kv.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
# skip:start
from typegraph import Graph, Policy, typegraph
from typegraph.graph.params import Cors
from typegraph.runtimes.kv import KvRuntime

# skip:end


@typegraph(
# skip:start
cors=Cors(allow_origin=["https://metatype.dev", "http://localhost:3000"]),
# skip:end
)
def key_value(g: Graph):
kv = KvRuntime("REDIS")

g.expose(
Policy.public(),
get=kv.get(),
set=kv.set(),
delete=kv.delete(),
keys=kv.keys(),
values=kv.values(),
)
24 changes: 24 additions & 0 deletions examples/typegraphs/kv.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
// skip:start
import { Policy, typegraph } from "@typegraph/sdk/index.ts";
import { KvRuntime } from "@typegraph/sdk/runtimes/kv.ts";

// skip:end

export const tg = await typegraph(
{
name: "key-value",
// skip:next-line
cors: { allowOrigin: ["https://metatype.dev", "http://localhost:3000"] },
},
(g) => {
const kv = new KvRuntime("REDIS");
const pub = Policy.public();
g.expose({
get: kv.get(),
set: kv.set(),
delete: kv.delete(),
keys: kv.keys(),
values: kv.values(),
}, pub);
},
);
2 changes: 1 addition & 1 deletion examples/typegraphs/metagen/rs/mdk.rs
Original file line number Diff line number Diff line change
Expand Up @@ -109,7 +109,7 @@ impl Router {
}

pub fn init(&self, args: InitArgs) -> Result<InitResponse, InitError> {
static MT_VERSION: &str = "0.4.7-0";
static MT_VERSION: &str = "0.4.8-0";
if args.metatype_version != MT_VERSION {
return Err(InitError::VersionMismatch(MT_VERSION.into()));
}
Expand Down
9 changes: 9 additions & 0 deletions libs/common/src/typegraph/runtimes/kv.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
// Copyright Metatype OÜ, licensed under the Elastic License 2.0.
// SPDX-License-Identifier: Elastic-2.0

use serde::{Deserialize, Serialize};

#[derive(Serialize, Deserialize, Clone, Debug)]
pub struct KvRuntimeData {
pub url: String,
}
4 changes: 4 additions & 0 deletions libs/common/src/typegraph/runtimes/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ use serde::{Deserialize, Serialize};
use self::deno::DenoRuntimeData;
use self::graphql::GraphQLRuntimeData;
use self::http::HTTPRuntimeData;
use self::kv::KvRuntimeData;
use self::prisma::PrismaRuntimeData;
use self::python::PythonRuntimeData;
use self::random::RandomRuntimeData;
Expand All @@ -19,6 +20,7 @@ use self::wasm::WasmRuntimeData;
pub mod deno;
pub mod graphql;
pub mod http;
pub mod kv;
pub mod prisma;
pub mod python;
pub mod random;
Expand Down Expand Up @@ -53,6 +55,7 @@ pub enum KnownRuntime {
WasmWire(WasmRuntimeData),
Typegate(TypegateRuntimeData),
Typegraph(TypegraphRuntimeData),
Kv(KvRuntimeData),
}

#[derive(Serialize, Deserialize, Clone, Debug, Default)]
Expand Down Expand Up @@ -85,6 +88,7 @@ impl TGRuntime {
KnownRuntime::WasmReflected(_) => "wasm_reflected",
KnownRuntime::Typegate(_) => "typegate",
KnownRuntime::Typegraph(_) => "typegraph",
KnownRuntime::Kv(_) => "kv",
},
TGRuntime::Unknown(UnknownRuntime { name, .. }) => name,
}
Expand Down
89 changes: 89 additions & 0 deletions typegate/src/runtimes/kv.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,89 @@
// Copyright Metatype OÜ, licensed under the Elastic License 2.0.
// SPDX-License-Identifier: Elastic-2.0

import { connect, parseURL, Redis } from "redis";
import { ComputeStage } from "../engine/query_engine.ts";
import { getLogger, Logger } from "../log.ts";
import { TypeGraph } from "../typegraph/mod.ts";
import { KvRuntimeData } from "../typegraph/types.ts";
import { Resolver, RuntimeInitParams } from "../types.ts";
import { registerRuntime } from "./mod.ts";
import { Runtime } from "./Runtime.ts";

const logger = getLogger(import.meta);

@registerRuntime("kv")
export class KvRuntime extends Runtime {
private logger: Logger;
private redis: Redis;

private constructor(typegraphName: string, redis: Redis) {
super(typegraphName);
this.logger = getLogger(`kv:'${typegraphName}'`);
this.redis = redis;
}

static async init(params: RuntimeInitParams): Promise<Runtime> {
logger.info("Initializing KvRuntime");
logger.debug(`Init params: ${JSON.stringify(params)}`);
const { typegraph, args, secretManager } = params as RuntimeInitParams<
KvRuntimeData
>;
const typegraphName = TypeGraph.formatName(typegraph);
const url = secretManager.secretOrFail(args.url);
const redisConnectionOption = parseURL(url);
const connection = await connect(redisConnectionOption);
const instance = new KvRuntime(typegraphName, connection);
instance.logger.info("Registered KvRuntime");

return instance;
}

// deno-lint-ignore require-await
async deinit(): Promise<void> {
this.redis.close();
}

materialize(
stage: ComputeStage,
_waitlist: ComputeStage[],
_verbose: boolean,
): ComputeStage[] | Promise<ComputeStage[]> {
const name = stage.props.materializer?.name;

const resolver: Resolver = async (args) => {
if (name == "kv_set") {
const { key, value } = args;
return await this.redis.set(key, value);
}

if (name == "kv_get") {
const { key } = args;
return await this.redis.get(key);
}

if (name == "kv_delete") {
const { key } = args;
return await this.redis.del(key);
}

if (name == "kv_keys") {
const { filter } = args;
return await this.redis.keys(filter ?? "*");
}

if (name === "kv_values") {
const { filter } = args;
const keys = await this.redis.keys(filter ?? "*");
const values = await Promise.all(
keys.map(async (key) => {
const value = await this.redis.get(key);
return value;
}),
);
return values;
}
};
return [new ComputeStage({ ...stage.props, resolver })];
}
}
1 change: 1 addition & 0 deletions typegate/src/runtimes/mod.ts
Original file line number Diff line number Diff line change
Expand Up @@ -48,5 +48,6 @@ export async function init_runtimes(): Promise<void> {
import("./typegraph.ts"),
import("./wasm_wire.ts"),
import("./wasm_reflected.ts"),
import("./kv.ts"),
]);
}
4 changes: 4 additions & 0 deletions typegate/src/typegraph/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -561,3 +561,7 @@ export interface WasiMatData {
func: string;
wasmArtifact: string;
}

export interface KvRuntimeData {
url: string;
}
1 change: 1 addition & 0 deletions typegate/tests/e2e/website/website_test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ const list = [
"index",
"injections",
"jwt",
"kv",
"math",
"metagen-deno",
"metagen-py",
Expand Down
Loading

0 comments on commit 54da279

Please sign in to comment.