Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(client): inject transport #700

Open
wants to merge 5 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 20 additions & 6 deletions src/components/client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ import { template } from "lodash";

const tsTemplate = template(`
// Code generated by @open-rpc/generator DO NOT EDIT.
import { RequestManager, PostMessageWindowTransport, PostMessageIframeTransport, WebSocketTransport, HTTPTransport, Client, JSONRPCError } from "@open-rpc/client-js";
import { RequestManager, PostMessageWindowTransport, PostMessageIframeTransport, WebSocketTransport, HTTPTransport, Transport, Client, JSONRPCError } from "@open-rpc/client-js";
import _ from "lodash";
import { OpenrpcDocument as OpenRPC, MethodObject, ContentDescriptorObject } from "@open-rpc/meta-schema";
import { MethodCallValidator, MethodNotFoundError } from "@open-rpc/schema-utils-js";
Expand All @@ -19,18 +19,19 @@ import { MethodCallValidator, MethodNotFoundError } from "@open-rpc/schema-utils

export interface Options {
transport: {
type: "websocket" | "http" | "https" | "postmessagewindow" | "postmessageiframe";
type: "websocket" | "http" | "https" | "postmessagewindow" | "postmessageiframe" | "injected";
host: string;
port: number;
path?: string;
protocol?: string;
injected: Transport;
},
}

export class <%= className %> {
public rpc: Client;
public static openrpcDocument: OpenRPC = <%= JSON.stringify(openrpcDocument) %> ;
public transport: HTTPTransport | WebSocketTransport | PostMessageWindowTransport | PostMessageIframeTransport;
public transport: HTTPTransport | WebSocketTransport | PostMessageWindowTransport | PostMessageIframeTransport | Transport;
private validator: MethodCallValidator;
private timeout: number | undefined;

Expand All @@ -39,12 +40,21 @@ export class <%= className %> {
if (options.transport === undefined || options.transport.type === undefined) {
throw new Error("Invalid constructor params");
}
const {type, host, port, protocol} = options.transport;

const {type, host, port, protocol, injected} = options.transport;

if (type === "injected" && injected === undefined) {
throw new Error("Missing injected transport");
}

let path = options.transport.path || "";
if(path && path[0] !== "/") {
path = "/" + path;
}
switch (type) {
case 'injected':
this.transport = injected;
break;
case 'http':
case 'https':
this.transport = new HTTPTransport((protocol || type) + "://" + host + ":" + port + path);
Expand Down Expand Up @@ -176,7 +186,11 @@ const hooks: IHooks = {
afterCopyStatic: [
async (dest, frm, component): Promise<void> => {
if (component.language === "typescript") {
return await move(path.join(dest, "_package.json"), path.join(dest, "package.json"), { overwrite: true });
return await move(
path.join(dest, "_package.json"),
path.join(dest, "package.json"),
{ overwrite: true }
);
}
},
],
Expand All @@ -202,7 +216,7 @@ const hooks: IHooks = {
const updatedCargo = TOML.stringify({
...cargoTOML,
package: {
...cargoTOML.package as object,
...(cargoTOML.package as object),
name: component.name,
version: openrpcDocument.info.version,
},
Expand Down
37 changes: 25 additions & 12 deletions src/custom-test-component.js
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
const path = require("path");
const { move, readFile, writeFile } =require("fs-extra");
const _ = require('lodash')
const components = require("./components")
const { move, readFile, writeFile } = require("fs-extra");
const _ = require("lodash");
const components = require("./components");
const { getDefaultComponentTemplatePath } = components;

const { template } = _;
const tsTemplate = template(`
// Code generated by @custom-test generator DO NOT EDIT.
import { RequestManager, PostMessageWindowTransport, PostMessageIframeTransport, WebSocketTransport, HTTPTransport, Client, JSONRPCError } from "@open-rpc/client-js";
import { RequestManager, PostMessageWindowTransport, PostMessageIframeTransport, WebSocketTransport, HTTPTransport, Transport, Client, JSONRPCError } from "@open-rpc/client-js";
import _ from "lodash";
import { OpenrpcDocument as OpenRPC, MethodObject, ContentDescriptorObject } from "@open-rpc/meta-schema";
import { MethodCallValidator, MethodNotFoundError } from "@open-rpc/schema-utils-js";
Expand All @@ -16,18 +16,19 @@ import { MethodCallValidator, MethodNotFoundError } from "@open-rpc/schema-utils

export interface Options {
transport: {
type: "websocket" | "http" | "https" | "postmessagewindow" | "postmessageiframe";
type: "websocket" | "http" | "https" | "postmessagewindow" | "postmessageiframe" | "injected";
host: string;
port: number;
path?: string;
protocol?: string;
transport?: Transport;
},
}

export class <%= className %> {
public rpc: Client;
public static openrpcDocument: OpenRPC = <%= JSON.stringify(openrpcDocument) %> ;
public transport: HTTPTransport | WebSocketTransport | PostMessageWindowTransport | PostMessageIframeTransport;
public transport: HTTPTransport | WebSocketTransport | PostMessageWindowTransport | PostMessageIframeTransport | Transport;
private validator: MethodCallValidator;
private timeout: number | undefined;

Expand All @@ -36,12 +37,22 @@ export class <%= className %> {
if (options.transport === undefined || options.transport.type === undefined) {
throw new Error("Invalid constructor params");
}
const {type, host, port, protocol} = options.transport;

const {type, host, port, protocol, injected} = options.transport;

if (type === "injected" && injected === undefined) {
throw new Error("Missing injected transport");
}

let path = options.transport.path || "";
if(path && path[0] !== "/") {
path = "/" + path;
}

switch (type) {
case 'injected':
this.transport = injected
break;
case 'http':
case 'https':
this.transport = new HTTPTransport((protocol || type) + "://" + host + ":" + port + path);
Expand Down Expand Up @@ -158,12 +169,15 @@ export class <%= className %> {
export default <%= className %>;
`);


const hooks = {
afterCopyStatic: [
async (dest, frm, component) => {
if (component.language === "typescript") {
return await move(path.join(dest, "_package.json"), path.join(dest, "package.json"), { overwrite: true });
return await move(
path.join(dest, "_package.json"),
path.join(dest, "package.json"),
{ overwrite: true }
);
}
},
],
Expand Down Expand Up @@ -193,8 +207,7 @@ const hooks = {
},
};


module.exports = {
hooks,
staticPath: getDefaultComponentTemplatePath
}
staticPath: getDefaultComponentTemplatePath,
};
104 changes: 80 additions & 24 deletions src/index.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,10 @@ import fsx, { emptyDir } from "fs-extra";
import examples from "@open-rpc/examples";
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

changes to this file are just prettier rules applied

import { promisify } from "util";
import { forEach } from "lodash";
import { parseOpenRPCDocument, OpenRPCDocumentDereferencingError } from "@open-rpc/schema-utils-js";
import {
parseOpenRPCDocument,
OpenRPCDocumentDereferencingError,
} from "@open-rpc/schema-utils-js";
import { OpenrpcDocument as OpenRPC } from "@open-rpc/meta-schema";

const stat = promisify(fs.stat);
Expand Down Expand Up @@ -34,9 +37,7 @@ describe(`Examples to generate Js clients`, () => {
methods: [
{
name: "foo",
params: [
{ $ref: "#/components/contentDescriptors/LeFoo" },
],
params: [{ $ref: "#/components/contentDescriptors/LeFoo" }],
result: {
name: "bar",
schema: { $ref: "#/components/contentDescriptors/LeFoo" },
Expand All @@ -61,19 +62,20 @@ describe(`Examples to generate Js clients`, () => {
};
const genProm = clientGen(testDocument);

return expect(genProm).rejects.toBeInstanceOf(OpenRPCDocumentDereferencingError);
return expect(genProm).rejects.toBeInstanceOf(
OpenRPCDocumentDereferencingError
);
});


forEach(examples, (example: OpenRPC, exampleName: string) => {
it(`rejects configurations without outDir or outPath`, async ()=>{
const promGen = clientGen({
openrpcDocument: await parseOpenRPCDocument(example),
components: [
{ type: "client", language: "typescript", name: "testclient-ts" },
]
});
expect(promGen).rejects.toBeInstanceOf(Error);
it(`rejects configurations without outDir or outPath`, async () => {
const promGen = clientGen({
openrpcDocument: await parseOpenRPCDocument(example),
components: [
{ type: "client", language: "typescript", name: "testclient-ts" },
],
});
expect(promGen).rejects.toBeInstanceOf(Error);
});

it(`creates a new client for example: ${exampleName} and regenerates after`, async () => {
Expand All @@ -88,11 +90,38 @@ describe(`Examples to generate Js clients`, () => {
{ type: "client", language: "typescript", name: "testclient-ts" },
{ type: "server", language: "typescript", name: "testserver-ts" },
{ type: "docs", language: "gatsby", name: "testserver-gatsby" },
{ type: "custom", language: "typescript", name: "custom-stuff", "customComponent":"./src/custom-test-component.js", customType:"client"},
{ type: "custom", language: "typescript", name: "custom-stuff2", "customComponent":"./src/custom-test-component.js", customType:"client", openRPCPath: null},
{ type: "custom", language: "typescript", name: "custom-stuff3", "customComponent":"./src/custom-test-component.js", customType:"client", openRPCPath: "tmpz"},
{ type: "custom", language: "typescript", name: "custom-stuff4", "customComponent":"./src/custom-test-component.js", customType:"client",
openRPCPath: "tmpy", outPath: `${exampleOutDir}/special`}
{
type: "custom",
language: "typescript",
name: "custom-stuff",
customComponent: "./src/custom-test-component.js",
customType: "client",
},
{
type: "custom",
language: "typescript",
name: "custom-stuff2",
customComponent: "./src/custom-test-component.js",
customType: "client",
openRPCPath: null,
},
{
type: "custom",
language: "typescript",
name: "custom-stuff3",
customComponent: "./src/custom-test-component.js",
customType: "client",
openRPCPath: "tmpz",
},
{
type: "custom",
language: "typescript",
name: "custom-stuff4",
customComponent: "./src/custom-test-component.js",
customType: "client",
openRPCPath: "tmpy",
outPath: `${exampleOutDir}/special`,
},
],
});

Expand All @@ -107,11 +136,38 @@ describe(`Examples to generate Js clients`, () => {
{ type: "client", language: "typescript", name: "testclient-ts" },
{ type: "server", language: "typescript", name: "testserver-ts" },
{ type: "docs", language: "gatsby", name: "testserver-gatsby" },
{ type: "custom", language: "typescript", name: "custom-stuff", "customComponent":"./src/custom-test-component.js", customType:"client"},
{ type: "custom", language: "typescript", name: "custom-stuff2", "customComponent":"./src/custom-test-component.js", customType:"client", openRPCPath: null},
{ type: "custom", language: "typescript", name: "custom-stuff3", "customComponent":"./src/custom-test-component.js", customType:"client", openRPCPath: "tmpz"},
{ type: "custom", language: "typescript", name: "custom-stuff4", "customComponent":"./src/custom-test-component.js", customType:"client",
openRPCPath: "tmpy", outPath: `${exampleOutDir}/special`}
{
type: "custom",
language: "typescript",
name: "custom-stuff",
customComponent: "./src/custom-test-component.js",
customType: "client",
},
{
type: "custom",
language: "typescript",
name: "custom-stuff2",
customComponent: "./src/custom-test-component.js",
customType: "client",
openRPCPath: null,
},
{
type: "custom",
language: "typescript",
name: "custom-stuff3",
customComponent: "./src/custom-test-component.js",
customType: "client",
openRPCPath: "tmpz",
},
{
type: "custom",
language: "typescript",
name: "custom-stuff4",
customComponent: "./src/custom-test-component.js",
customType: "client",
openRPCPath: "tmpy",
outPath: `${exampleOutDir}/special`,
},
],
});

Expand Down