From 97c4bdcc4c01cb5c0969c67d8dfd349b27d7265e Mon Sep 17 00:00:00 2001 From: nabarun Date: Wed, 24 May 2023 17:27:10 +0530 Subject: [PATCH 1/5] Setup server package to use and instantiate P2PMessageService --- .../p2p-message-service/service.ts | 2 +- packages/nitro-client/webpack.common.ts | 13 ++-- packages/server/.gitignore | 3 + packages/server/package.json | 19 +++++ packages/server/src/index.ts | 46 ++++++++++++ packages/server/tsconfig.json | 74 +++++++++++++++++++ yarn.lock | 4 +- 7 files changed, 153 insertions(+), 8 deletions(-) create mode 100644 packages/server/.gitignore create mode 100644 packages/server/package.json create mode 100644 packages/server/src/index.ts create mode 100644 packages/server/tsconfig.json diff --git a/packages/nitro-client/src/client/engine/messageservice/p2p-message-service/service.ts b/packages/nitro-client/src/client/engine/messageservice/p2p-message-service/service.ts index 3e5cb558..aec0abc0 100644 --- a/packages/nitro-client/src/client/engine/messageservice/p2p-message-service/service.ts +++ b/packages/nitro-client/src/client/engine/messageservice/p2p-message-service/service.ts @@ -103,7 +103,7 @@ export class P2PMessageService { me: Address, pk: Uint8Array, useMdnsPeerDiscovery: boolean, - logWriter: WritableStream, + logWriter?: WritableStream, ): Promise { const ms = new P2PMessageService({ toEngine: Channel(BUFFER_SIZE), diff --git a/packages/nitro-client/webpack.common.ts b/packages/nitro-client/webpack.common.ts index 4b1d1731..a3b282e0 100644 --- a/packages/nitro-client/webpack.common.ts +++ b/packages/nitro-client/webpack.common.ts @@ -27,19 +27,22 @@ const baseConfig: webpack.Configuration = { ], }, externals: { - '@chainsafe/libp2p-yamux': '@chainsafe/libp2p-yamux', - '@libp2p/crypto': '@libp2p/crypto', - '@libp2p/mdns': '@libp2p/mdns', - '@libp2p/tcp': '@libp2p/tcp', '@nodeguy/channel': '@nodeguy/channel', debug: 'debug', ethers: 'ethers', - libp2p: 'libp2p', }, }; export const browserConfig: webpack.Configuration = merge(baseConfig, { entry: './src/browser.ts', + // Packages are resolved properly in browser build tool; so not required in build output + externals: { + '@chainsafe/libp2p-yamux': '@chainsafe/libp2p-yamux', + '@libp2p/crypto': '@libp2p/crypto', + '@libp2p/mdns': '@libp2p/mdns', + '@libp2p/tcp': '@libp2p/tcp', + libp2p: 'libp2p', + }, }); export const nodeConfig: webpack.Configuration = merge(baseConfig, { diff --git a/packages/server/.gitignore b/packages/server/.gitignore new file mode 100644 index 00000000..7d4f0ad5 --- /dev/null +++ b/packages/server/.gitignore @@ -0,0 +1,3 @@ +node_modules/ + +dist diff --git a/packages/server/package.json b/packages/server/package.json new file mode 100644 index 00000000..8196101d --- /dev/null +++ b/packages/server/package.json @@ -0,0 +1,19 @@ +{ + "name": "@cerc-io/server", + "version": "0.1.0", + "main": "index.js", + "license": "MIT", + "private": true, + "devDependencies": { + "typescript": "^5.0.4" + }, + "scripts": { + "build": "tsc", + "start": "DEBUG=ts-nitro:* node --enable-source-maps dist/index.js" + }, + "dependencies": { + "debug": "^4.3.4", + "yargs": "^17.7.2", + "@cerc-io/nitro-client": "^0.1.0" + } +} diff --git a/packages/server/src/index.ts b/packages/server/src/index.ts new file mode 100644 index 00000000..eb5f7072 --- /dev/null +++ b/packages/server/src/index.ts @@ -0,0 +1,46 @@ +import yargs from 'yargs'; +import debug from 'debug'; + +import { P2PMessageService } from '@cerc-io/nitro-client'; + +const log = debug('ts-nitro:server') + +const getArgv = () => { + return yargs.parserConfiguration({ + 'parse-numbers': false + }).options({ + port: { + alias: 'p', + type: 'number', + require: true, + demandOption: true, + describe: 'Message service port', + }, + }).argv; +} + +const main = async () => { + const argv = getArgv(); + + const keys = await import('@libp2p/crypto/keys'); + + // TODO: Generate private key from a string + const privateKey = await keys.generateKeyPair('Ed25519'); + + const p2pMessageService = await P2PMessageService.newMessageService( + '127.0.0.1', + argv.port, + // TODO: Pass account address + '', + privateKey.bytes, + true + ) + + console.log('p2pMessageService key', p2pMessageService) +} + +main().catch(err => { + log(err); +}).finally(() => { + process.exit(0); +}); diff --git a/packages/server/tsconfig.json b/packages/server/tsconfig.json new file mode 100644 index 00000000..c9a43c7f --- /dev/null +++ b/packages/server/tsconfig.json @@ -0,0 +1,74 @@ +{ + "compilerOptions": { + /* Visit https://aka.ms/tsconfig.json to read more about this file */ + + /* Basic Options */ + // "incremental": true, /* Enable incremental compilation */ + "target": "es5", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', 'ES2018', 'ES2019', 'ES2020', 'ES2021', or 'ESNEXT'. */ + "module": "CommonJS", /* Specify module code generation: 'none', 'commonjs', 'amd', 'system', 'umd', 'es2015', 'es2020', or 'ESNext'. */ + "lib": [ "ES5", "ES6", "ES2020" ], /* Specify library files to be included in the compilation. */ + // "allowJs": true, /* Allow javascript files to be compiled. */ + // "checkJs": true, /* Report errors in .js files. */ + // "jsx": "preserve", /* Specify JSX code generation: 'preserve', 'react-native', 'react', 'react-jsx' or 'react-jsxdev'. */ + "declaration": true, /* Generates corresponding '.d.ts' file. */ + // "declarationMap": true, /* Generates a sourcemap for each corresponding '.d.ts' file. */ + "sourceMap": true, /* Generates corresponding '.map' file. */ + // "outFile": "./", /* Concatenate and emit output to single file. */ + "outDir": "dist", /* Redirect output structure to the directory. */ + // "rootDir": "./", /* Specify the root directory of input files. Use to control the output directory structure with --outDir. */ + // "composite": true, /* Enable project compilation */ + // "tsBuildInfoFile": "./", /* Specify file to store incremental compilation information */ + // "removeComments": true, /* Do not emit comments to output. */ + // "noEmit": true, /* Do not emit outputs. */ + // "importHelpers": true, /* Import emit helpers from 'tslib'. */ + "downlevelIteration": true, /* Provide full support for iterables in 'for-of', spread, and destructuring when targeting 'ES5' or 'ES3'. */ + // "isolatedModules": true, /* Transpile each file as a separate module (similar to 'ts.transpileModule'). */ + + /* Strict Type-Checking Options */ + "strict": true, /* Enable all strict type-checking options. */ + // "noImplicitAny": true, /* Raise error on expressions and declarations with an implied 'any' type. */ + // "strictNullChecks": true, /* Enable strict null checks. */ + // "strictFunctionTypes": true, /* Enable strict checking of function types. */ + // "strictBindCallApply": true, /* Enable strict 'bind', 'call', and 'apply' methods on functions. */ + // "strictPropertyInitialization": true, /* Enable strict checking of property initialization in classes. */ + // "noImplicitThis": true, /* Raise error on 'this' expressions with an implied 'any' type. */ + // "alwaysStrict": true, /* Parse in strict mode and emit "use strict" for each source file. */ + + /* Additional Checks */ + // "noUnusedLocals": true, /* Report errors on unused locals. */ + // "noUnusedParameters": true, /* Report errors on unused parameters. */ + // "noImplicitReturns": true, /* Report error when not all code paths in function return a value. */ + // "noFallthroughCasesInSwitch": true, /* Report errors for fallthrough cases in switch statement. */ + // "noUncheckedIndexedAccess": true, /* Include 'undefined' in index signature results */ + // "noImplicitOverride": true, /* Ensure overriding members in derived classes are marked with an 'override' modifier. */ + // "noPropertyAccessFromIndexSignature": true, /* Require undeclared properties from index signatures to use element accesses. */ + + /* Module Resolution Options */ + "moduleResolution": "Node16", /* Specify module resolution strategy: 'node' (Node.js) or 'classic' (TypeScript pre-1.6). */ + // "baseUrl": "./", /* Base directory to resolve non-absolute module names. */ + // "paths": {}, /* A series of entries which re-map imports to lookup locations relative to the 'baseUrl'. */ + // "rootDirs": [], /* List of root folders whose combined content represents the structure of the project at runtime. */ + "typeRoots": [], /* List of folders to include type definitions from. */ + // "types": [], /* Type declaration files to be included in compilation. */ + // "allowSyntheticDefaultImports": true, /* Allow default imports from modules with no default export. This does not affect code emit, just typechecking. */ + "esModuleInterop": true, /* Enables emit interoperability between CommonJS and ES Modules via creation of namespace objects for all imports. Implies 'allowSyntheticDefaultImports'. */ + // "preserveSymlinks": true, /* Do not resolve the real path of symlinks. */ + // "allowUmdGlobalAccess": true, /* Allow accessing UMD globals from modules. */ + + /* Source Map Options */ + // "sourceRoot": "", /* Specify the location where debugger should locate TypeScript files instead of source locations. */ + // "mapRoot": "", /* Specify the location where debugger should locate map files instead of generated locations. */ + // "inlineSourceMap": true, /* Emit a single file with source maps instead of having a separate file. */ + // "inlineSources": true, /* Emit the source alongside the sourcemaps within a single file; requires '--inlineSourceMap' or '--sourceMap' to be set. */ + + /* Experimental Options */ + "experimentalDecorators": true, /* Enables experimental support for ES7 decorators. */ + // "emitDecoratorMetadata": true, /* Enables experimental support for emitting type metadata for decorators. */ + + /* Advanced Options */ + "skipLibCheck": true, /* Skip type checking of declaration files. */ + "forceConsistentCasingInFileNames": true, /* Disallow inconsistently-cased references to the same file. */ + "resolveJsonModule": true /* Enabling the option allows importing JSON, and validating the types in that JSON file. */ + }, + "include": ["src/**/*"] +} diff --git a/yarn.lock b/yarn.lock index 9f177b70..a57b76fb 100644 --- a/yarn.lock +++ b/yarn.lock @@ -14571,9 +14571,9 @@ yargs@16.2.0, yargs@^16.2.0: y18n "^5.0.5" yargs-parser "^20.2.2" -yargs@^17.6.2: +yargs@^17.6.2, yargs@^17.7.2: version "17.7.2" - resolved "https://registry.npmjs.org/yargs/-/yargs-17.7.2.tgz" + resolved "https://registry.yarnpkg.com/yargs/-/yargs-17.7.2.tgz#991df39aca675a192b816e1e0363f9d75d2aa269" integrity sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w== dependencies: cliui "^8.0.1" From cce176f2cbb0d8a12a62946a7e57cbaa70f4f62e Mon Sep 17 00:00:00 2001 From: nabarun Date: Wed, 24 May 2023 17:55:32 +0530 Subject: [PATCH 2/5] Fix root level script for use in CI --- package.json | 4 ++-- packages/nitro-client/package.json | 1 + 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/package.json b/package.json index 12c53be6..a9e00f74 100644 --- a/package.json +++ b/package.json @@ -12,8 +12,8 @@ }, "scripts": { "lint": "lerna run lint --stream", - "build:browser": "lerna run build:browser,build --stream", - "build:node": "lerna run build:node,build --stream --ignore @cerc-io/example-web-app", + "build:browser": "TARGET=browser lerna run build --stream --ignore @cerc-io/server", + "build:node": "TARGET=node lerna run build --stream --ignore @cerc-io/example-web-app", "test:browser": "lerna run test --stream", "test:node": "lerna run test --stream --ignore @cerc-io/example-web-app" } diff --git a/packages/nitro-client/package.json b/packages/nitro-client/package.json index 24fcdbe5..ced77803 100644 --- a/packages/nitro-client/package.json +++ b/packages/nitro-client/package.json @@ -6,6 +6,7 @@ "scripts": { "index:browser": "cp src/browser.ts src/index.ts", "index:node": "cp src/node.ts src/index.ts", + "build": "if [ \"$TARGET\" = \"browser\" ]; then yarn build:browser; else yarn build:node; fi", "build:browser": "yarn index:browser && webpack --config webpack.prod.ts --env target=browser", "build:node": "yarn index:node && webpack --config webpack.prod.ts --env target=node", "build:dev:browser": "yarn index:browser && webpack --config webpack.dev.ts --env target=browser", From b30cd682d1128dbd9425ccbf67c8b7a44389a1ed Mon Sep 17 00:00:00 2001 From: nabarun Date: Wed, 24 May 2023 19:53:54 +0530 Subject: [PATCH 3/5] Implement handlePeerFound method --- .../p2p-message-service/service.ts | 31 +++- packages/server/src/index.ts | 14 +- packages/server/tsconfig.json | 157 +++++++++++------- 3 files changed, 129 insertions(+), 73 deletions(-) diff --git a/packages/nitro-client/src/client/engine/messageservice/p2p-message-service/service.ts b/packages/nitro-client/src/client/engine/messageservice/p2p-message-service/service.ts index aec0abc0..a574a45b 100644 --- a/packages/nitro-client/src/client/engine/messageservice/p2p-message-service/service.ts +++ b/packages/nitro-client/src/client/engine/messageservice/p2p-message-service/service.ts @@ -17,7 +17,7 @@ import type { Stream } from '@libp2p/interface-connection'; // @ts-expect-error import type { IncomingStreamData } from '@libp2p/interface-registrar'; // @ts-expect-error -import type { Multiaddr } from '@multiformats/multiaddr'; +import type { PeerInfo as Libp2pPeerInfo } from '@libp2p/interface-peer-info'; import { SyncMap } from '../../../../internal/safesync/safesync'; import { Message } from '../../../../protocols/messages'; @@ -118,7 +118,7 @@ export class P2PMessageService { try { const messageKey = await unmarshalPrivateKey(pk); ms.key = messageKey; - } catch (err: unknown) { + } catch (err) { ms.checkError(err as Error); } @@ -155,6 +155,8 @@ export class P2PMessageService { const host = await createLibp2p(options); ms.p2pHost = host; + ms.p2pHost.addEventListener('peer:discovery', ms.handlePeerFound.bind(ms)); + ms.p2pHost.handle(PROTOCOL_ID, ms.msgStreamHandler); ms.p2pHost.handle(PEER_EXCHANGE_PROTOCOL_ID, ({ stream }) => { @@ -171,7 +173,30 @@ export class P2PMessageService { // handlePeerFound is called by the mDNS service when a peer is found. // TODO: Implement and remove void - handlePeerFound(pi: Multiaddr[]) {} + async handlePeerFound({ detail: pi }: CustomEvent) { + assert(this.p2pHost); + + const peer = await this.p2pHost.peerStore.save( + pi.id, + { + multiaddrs: pi.multiaddrs, + // TODO: Check if ttl option exists to set it like in go-nitro + // peerstore.PermanentAddrTTL + }, + ); + + try { + const stream = await this.p2pHost.dialProtocol( + peer.id, + PEER_EXCHANGE_PROTOCOL_ID, + ); + + this.sendPeerInfo(stream); + stream.close(); + } catch (err) { + this.checkError(err as Error); + } + } // TODO: Implement private msgStreamHandler({ stream }: IncomingStreamData) {} diff --git a/packages/server/src/index.ts b/packages/server/src/index.ts index eb5f7072..18d8078b 100644 --- a/packages/server/src/index.ts +++ b/packages/server/src/index.ts @@ -34,13 +34,15 @@ const main = async () => { '', privateKey.bytes, true - ) - - console.log('p2pMessageService key', p2pMessageService) + ); } -main().catch(err => { +main().then(() => { + log('Started P2PMessageService'); +}).catch(err => { log(err); -}).finally(() => { - process.exit(0); +}); + +process.on('uncaughtException', err => { + log('uncaughtException', err); }); diff --git a/packages/server/tsconfig.json b/packages/server/tsconfig.json index c9a43c7f..19766e44 100644 --- a/packages/server/tsconfig.json +++ b/packages/server/tsconfig.json @@ -1,74 +1,103 @@ { "compilerOptions": { - /* Visit https://aka.ms/tsconfig.json to read more about this file */ + /* Visit https://aka.ms/tsconfig to read more about this file */ - /* Basic Options */ - // "incremental": true, /* Enable incremental compilation */ - "target": "es5", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', 'ES2018', 'ES2019', 'ES2020', 'ES2021', or 'ESNEXT'. */ - "module": "CommonJS", /* Specify module code generation: 'none', 'commonjs', 'amd', 'system', 'umd', 'es2015', 'es2020', or 'ESNext'. */ - "lib": [ "ES5", "ES6", "ES2020" ], /* Specify library files to be included in the compilation. */ - // "allowJs": true, /* Allow javascript files to be compiled. */ - // "checkJs": true, /* Report errors in .js files. */ - // "jsx": "preserve", /* Specify JSX code generation: 'preserve', 'react-native', 'react', 'react-jsx' or 'react-jsxdev'. */ - "declaration": true, /* Generates corresponding '.d.ts' file. */ - // "declarationMap": true, /* Generates a sourcemap for each corresponding '.d.ts' file. */ - "sourceMap": true, /* Generates corresponding '.map' file. */ - // "outFile": "./", /* Concatenate and emit output to single file. */ - "outDir": "dist", /* Redirect output structure to the directory. */ - // "rootDir": "./", /* Specify the root directory of input files. Use to control the output directory structure with --outDir. */ - // "composite": true, /* Enable project compilation */ - // "tsBuildInfoFile": "./", /* Specify file to store incremental compilation information */ - // "removeComments": true, /* Do not emit comments to output. */ - // "noEmit": true, /* Do not emit outputs. */ - // "importHelpers": true, /* Import emit helpers from 'tslib'. */ - "downlevelIteration": true, /* Provide full support for iterables in 'for-of', spread, and destructuring when targeting 'ES5' or 'ES3'. */ - // "isolatedModules": true, /* Transpile each file as a separate module (similar to 'ts.transpileModule'). */ + /* Projects */ + // "incremental": true, /* Save .tsbuildinfo files to allow for incremental compilation of projects. */ + // "composite": true, /* Enable constraints that allow a TypeScript project to be used with project references. */ + // "tsBuildInfoFile": "./.tsbuildinfo", /* Specify the path to .tsbuildinfo incremental compilation file. */ + // "disableSourceOfProjectReferenceRedirect": true, /* Disable preferring source files instead of declaration files when referencing composite projects. */ + // "disableSolutionSearching": true, /* Opt a project out of multi-project reference checking when editing. */ + // "disableReferencedProjectLoad": true, /* Reduce the number of projects loaded automatically by TypeScript. */ - /* Strict Type-Checking Options */ - "strict": true, /* Enable all strict type-checking options. */ - // "noImplicitAny": true, /* Raise error on expressions and declarations with an implied 'any' type. */ - // "strictNullChecks": true, /* Enable strict null checks. */ - // "strictFunctionTypes": true, /* Enable strict checking of function types. */ - // "strictBindCallApply": true, /* Enable strict 'bind', 'call', and 'apply' methods on functions. */ - // "strictPropertyInitialization": true, /* Enable strict checking of property initialization in classes. */ - // "noImplicitThis": true, /* Raise error on 'this' expressions with an implied 'any' type. */ - // "alwaysStrict": true, /* Parse in strict mode and emit "use strict" for each source file. */ + /* Language and Environment */ + "target": "es2016", /* Set the JavaScript language version for emitted JavaScript and include compatible library declarations. */ + // "lib": [], /* Specify a set of bundled library declaration files that describe the target runtime environment. */ + // "jsx": "preserve", /* Specify what JSX code is generated. */ + // "experimentalDecorators": true, /* Enable experimental support for TC39 stage 2 draft decorators. */ + // "emitDecoratorMetadata": true, /* Emit design-type metadata for decorated declarations in source files. */ + // "jsxFactory": "", /* Specify the JSX factory function used when targeting React JSX emit, e.g. 'React.createElement' or 'h'. */ + // "jsxFragmentFactory": "", /* Specify the JSX Fragment reference used for fragments when targeting React JSX emit e.g. 'React.Fragment' or 'Fragment'. */ + // "jsxImportSource": "", /* Specify module specifier used to import the JSX factory functions when using 'jsx: react-jsx*'. */ + // "reactNamespace": "", /* Specify the object invoked for 'createElement'. This only applies when targeting 'react' JSX emit. */ + // "noLib": true, /* Disable including any library files, including the default lib.d.ts. */ + // "useDefineForClassFields": true, /* Emit ECMAScript-standard-compliant class fields. */ + // "moduleDetection": "auto", /* Control what method is used to detect module-format JS files. */ - /* Additional Checks */ - // "noUnusedLocals": true, /* Report errors on unused locals. */ - // "noUnusedParameters": true, /* Report errors on unused parameters. */ - // "noImplicitReturns": true, /* Report error when not all code paths in function return a value. */ - // "noFallthroughCasesInSwitch": true, /* Report errors for fallthrough cases in switch statement. */ - // "noUncheckedIndexedAccess": true, /* Include 'undefined' in index signature results */ - // "noImplicitOverride": true, /* Ensure overriding members in derived classes are marked with an 'override' modifier. */ - // "noPropertyAccessFromIndexSignature": true, /* Require undeclared properties from index signatures to use element accesses. */ + /* Modules */ + "module": "CommonJS", /* Specify what module code is generated. */ + // "rootDir": "./", /* Specify the root folder within your source files. */ + "moduleResolution": "node16", /* Specify how TypeScript looks up a file from a given module specifier. */ + // "baseUrl": "./", /* Specify the base directory to resolve non-relative module names. */ + // "paths": {}, /* Specify a set of entries that re-map imports to additional lookup locations. */ + // "rootDirs": [], /* Allow multiple folders to be treated as one when resolving modules. */ + // "typeRoots": [], /* Specify multiple folders that act like './node_modules/@types'. */ + // "types": [], /* Specify type package names to be included without being referenced in a source file. */ + // "allowUmdGlobalAccess": true, /* Allow accessing UMD globals from modules. */ + // "moduleSuffixes": [], /* List of file name suffixes to search when resolving a module. */ + // "resolveJsonModule": true, /* Enable importing .json files. */ + // "noResolve": true, /* Disallow 'import's, 'require's or ''s from expanding the number of files TypeScript should add to a project. */ - /* Module Resolution Options */ - "moduleResolution": "Node16", /* Specify module resolution strategy: 'node' (Node.js) or 'classic' (TypeScript pre-1.6). */ - // "baseUrl": "./", /* Base directory to resolve non-absolute module names. */ - // "paths": {}, /* A series of entries which re-map imports to lookup locations relative to the 'baseUrl'. */ - // "rootDirs": [], /* List of root folders whose combined content represents the structure of the project at runtime. */ - "typeRoots": [], /* List of folders to include type definitions from. */ - // "types": [], /* Type declaration files to be included in compilation. */ - // "allowSyntheticDefaultImports": true, /* Allow default imports from modules with no default export. This does not affect code emit, just typechecking. */ - "esModuleInterop": true, /* Enables emit interoperability between CommonJS and ES Modules via creation of namespace objects for all imports. Implies 'allowSyntheticDefaultImports'. */ - // "preserveSymlinks": true, /* Do not resolve the real path of symlinks. */ - // "allowUmdGlobalAccess": true, /* Allow accessing UMD globals from modules. */ + /* JavaScript Support */ + // "allowJs": true, /* Allow JavaScript files to be a part of your program. Use the 'checkJS' option to get errors from these files. */ + // "checkJs": true, /* Enable error reporting in type-checked JavaScript files. */ + // "maxNodeModuleJsDepth": 1, /* Specify the maximum folder depth used for checking JavaScript files from 'node_modules'. Only applicable with 'allowJs'. */ - /* Source Map Options */ - // "sourceRoot": "", /* Specify the location where debugger should locate TypeScript files instead of source locations. */ - // "mapRoot": "", /* Specify the location where debugger should locate map files instead of generated locations. */ - // "inlineSourceMap": true, /* Emit a single file with source maps instead of having a separate file. */ - // "inlineSources": true, /* Emit the source alongside the sourcemaps within a single file; requires '--inlineSourceMap' or '--sourceMap' to be set. */ + /* Emit */ + // "declaration": true, /* Generate .d.ts files from TypeScript and JavaScript files in your project. */ + // "declarationMap": true, /* Create sourcemaps for d.ts files. */ + // "emitDeclarationOnly": true, /* Only output d.ts files and not JavaScript files. */ + "sourceMap": true, /* Create source map files for emitted JavaScript files. */ + // "outFile": "./", /* Specify a file that bundles all outputs into one JavaScript file. If 'declaration' is true, also designates a file that bundles all .d.ts output. */ + "outDir": "dist", /* Specify an output folder for all emitted files. */ + // "removeComments": true, /* Disable emitting comments. */ + // "noEmit": true, /* Disable emitting files from a compilation. */ + // "importHelpers": true, /* Allow importing helper functions from tslib once per project, instead of including them per-file. */ + // "importsNotUsedAsValues": "remove", /* Specify emit/checking behavior for imports that are only used for types. */ + // "downlevelIteration": true, /* Emit more compliant, but verbose and less performant JavaScript for iteration. */ + // "sourceRoot": "", /* Specify the root path for debuggers to find the reference source code. */ + // "mapRoot": "", /* Specify the location where debugger should locate map files instead of generated locations. */ + // "inlineSourceMap": true, /* Include sourcemap files inside the emitted JavaScript. */ + // "inlineSources": true, /* Include source code in the sourcemaps inside the emitted JavaScript. */ + // "emitBOM": true, /* Emit a UTF-8 Byte Order Mark (BOM) in the beginning of output files. */ + // "newLine": "crlf", /* Set the newline character for emitting files. */ + // "stripInternal": true, /* Disable emitting declarations that have '@internal' in their JSDoc comments. */ + // "noEmitHelpers": true, /* Disable generating custom helper functions like '__extends' in compiled output. */ + // "noEmitOnError": true, /* Disable emitting files if any type checking errors are reported. */ + // "preserveConstEnums": true, /* Disable erasing 'const enum' declarations in generated code. */ + // "declarationDir": "./", /* Specify the output directory for generated declaration files. */ + // "preserveValueImports": true, /* Preserve unused imported values in the JavaScript output that would otherwise be removed. */ - /* Experimental Options */ - "experimentalDecorators": true, /* Enables experimental support for ES7 decorators. */ - // "emitDecoratorMetadata": true, /* Enables experimental support for emitting type metadata for decorators. */ + /* Interop Constraints */ + // "isolatedModules": true, /* Ensure that each file can be safely transpiled without relying on other imports. */ + // "allowSyntheticDefaultImports": true, /* Allow 'import x from y' when a module doesn't have a default export. */ + "esModuleInterop": true, /* Emit additional JavaScript to ease support for importing CommonJS modules. This enables 'allowSyntheticDefaultImports' for type compatibility. */ + // "preserveSymlinks": true, /* Disable resolving symlinks to their realpath. This correlates to the same flag in node. */ + "forceConsistentCasingInFileNames": true, /* Ensure that casing is correct in imports. */ - /* Advanced Options */ - "skipLibCheck": true, /* Skip type checking of declaration files. */ - "forceConsistentCasingInFileNames": true, /* Disallow inconsistently-cased references to the same file. */ - "resolveJsonModule": true /* Enabling the option allows importing JSON, and validating the types in that JSON file. */ - }, - "include": ["src/**/*"] + /* Type Checking */ + "strict": true, /* Enable all strict type-checking options. */ + // "noImplicitAny": true, /* Enable error reporting for expressions and declarations with an implied 'any' type. */ + // "strictNullChecks": true, /* When type checking, take into account 'null' and 'undefined'. */ + // "strictFunctionTypes": true, /* When assigning functions, check to ensure parameters and the return values are subtype-compatible. */ + // "strictBindCallApply": true, /* Check that the arguments for 'bind', 'call', and 'apply' methods match the original function. */ + // "strictPropertyInitialization": true, /* Check for class properties that are declared but not set in the constructor. */ + // "noImplicitThis": true, /* Enable error reporting when 'this' is given the type 'any'. */ + // "useUnknownInCatchVariables": true, /* Default catch clause variables as 'unknown' instead of 'any'. */ + // "alwaysStrict": true, /* Ensure 'use strict' is always emitted. */ + // "noUnusedLocals": true, /* Enable error reporting when local variables aren't read. */ + // "noUnusedParameters": true, /* Raise an error when a function parameter isn't read. */ + // "exactOptionalPropertyTypes": true, /* Interpret optional property types as written, rather than adding 'undefined'. */ + // "noImplicitReturns": true, /* Enable error reporting for codepaths that do not explicitly return in a function. */ + // "noFallthroughCasesInSwitch": true, /* Enable error reporting for fallthrough cases in switch statements. */ + // "noUncheckedIndexedAccess": true, /* Add 'undefined' to a type when accessed using an index. */ + // "noImplicitOverride": true, /* Ensure overriding members in derived classes are marked with an override modifier. */ + // "noPropertyAccessFromIndexSignature": true, /* Enforces using indexed accessors for keys declared using an indexed type. */ + // "allowUnusedLabels": true, /* Disable error reporting for unused labels. */ + // "allowUnreachableCode": true, /* Disable error reporting for unreachable code. */ + + /* Completeness */ + // "skipDefaultLibCheck": true, /* Skip type checking .d.ts files that are included with TypeScript. */ + "skipLibCheck": true /* Skip type checking all .d.ts files. */ + } } From bc381423c8fdec2b22481cc8ba43c07bfeb293bd Mon Sep 17 00:00:00 2001 From: nabarun Date: Thu, 25 May 2023 12:57:24 +0530 Subject: [PATCH 4/5] Setup lint in server package --- package.json | 2 +- .../p2p-message-service/service.ts | 2 - packages/server/.eslintignore | 5 +++ packages/server/.eslintrc.json | 18 +++++++++ packages/server/package.json | 13 ++++++- packages/server/src/index.ts | 38 +++++++++---------- packages/server/tsconfig.eslint.json | 4 ++ 7 files changed, 59 insertions(+), 23 deletions(-) create mode 100644 packages/server/.eslintignore create mode 100644 packages/server/.eslintrc.json create mode 100644 packages/server/tsconfig.eslint.json diff --git a/package.json b/package.json index a9e00f74..2f24befa 100644 --- a/package.json +++ b/package.json @@ -14,7 +14,7 @@ "lint": "lerna run lint --stream", "build:browser": "TARGET=browser lerna run build --stream --ignore @cerc-io/server", "build:node": "TARGET=node lerna run build --stream --ignore @cerc-io/example-web-app", - "test:browser": "lerna run test --stream", + "test:browser": "lerna run test --stream --ignore @cerc-io/server", "test:node": "lerna run test --stream --ignore @cerc-io/example-web-app" } } diff --git a/packages/nitro-client/src/client/engine/messageservice/p2p-message-service/service.ts b/packages/nitro-client/src/client/engine/messageservice/p2p-message-service/service.ts index a574a45b..93e16400 100644 --- a/packages/nitro-client/src/client/engine/messageservice/p2p-message-service/service.ts +++ b/packages/nitro-client/src/client/engine/messageservice/p2p-message-service/service.ts @@ -96,7 +96,6 @@ export class P2PMessageService { // newMessageService returns a running P2PMessageService listening on the given ip, port and message key. // If useMdnsPeerDiscovery is true, the message service will use mDNS to discover peers. // Otherwise, peers must be added manually via `AddPeers`. - // TODO: Implement and remove void static async newMessageService( ip: string, port: number, @@ -172,7 +171,6 @@ export class P2PMessageService { id(): string | void {} // handlePeerFound is called by the mDNS service when a peer is found. - // TODO: Implement and remove void async handlePeerFound({ detail: pi }: CustomEvent) { assert(this.p2pHost); diff --git a/packages/server/.eslintignore b/packages/server/.eslintignore new file mode 100644 index 00000000..653874b5 --- /dev/null +++ b/packages/server/.eslintignore @@ -0,0 +1,5 @@ +# Don't lint node_modules. +node_modules + +# Don't lint build output. +dist diff --git a/packages/server/.eslintrc.json b/packages/server/.eslintrc.json new file mode 100644 index 00000000..ed6cfd52 --- /dev/null +++ b/packages/server/.eslintrc.json @@ -0,0 +1,18 @@ +{ + "extends": [ + "semistandard", + "airbnb-base", + "airbnb-typescript/base" + ], + "parserOptions": { + "project": "./tsconfig.eslint.json" + }, + "rules": { + "import/no-extraneous-dependencies": [ + "error", + { + "devDependencies": ["test/**/*.test.ts"] + } + ] + } +} diff --git a/packages/server/package.json b/packages/server/package.json index 8196101d..8b12f25a 100644 --- a/packages/server/package.json +++ b/packages/server/package.json @@ -5,11 +5,22 @@ "license": "MIT", "private": true, "devDependencies": { + "@typescript-eslint/eslint-plugin": "^5.13.0", + "@typescript-eslint/parser": "^5.0.0", + "eslint": "^7.32.0 || ^8.2.0", + "eslint-config-airbnb-base": "^15.0.0", + "eslint-config-airbnb-typescript": "^17.0.0", + "eslint-config-semistandard": "^17.0.0", + "eslint-config-standard": "^17.0.0", + "eslint-plugin-import": "^2.25.3", + "eslint-plugin-n": "^15.0.0", + "eslint-plugin-promise": "^6.0.0", "typescript": "^5.0.4" }, "scripts": { "build": "tsc", - "start": "DEBUG=ts-nitro:* node --enable-source-maps dist/index.js" + "start": "DEBUG=ts-nitro:* node --enable-source-maps dist/index.js", + "lint": "eslint ." }, "dependencies": { "debug": "^4.3.4", diff --git a/packages/server/src/index.ts b/packages/server/src/index.ts index 18d8078b..6f088d09 100644 --- a/packages/server/src/index.ts +++ b/packages/server/src/index.ts @@ -3,21 +3,19 @@ import debug from 'debug'; import { P2PMessageService } from '@cerc-io/nitro-client'; -const log = debug('ts-nitro:server') - -const getArgv = () => { - return yargs.parserConfiguration({ - 'parse-numbers': false - }).options({ - port: { - alias: 'p', - type: 'number', - require: true, - demandOption: true, - describe: 'Message service port', - }, - }).argv; -} +const log = debug('ts-nitro:server'); + +const getArgv = () => yargs.parserConfiguration({ + 'parse-numbers': false, +}).options({ + port: { + alias: 'p', + type: 'number', + require: true, + demandOption: true, + describe: 'Message service port', + }, +}).argv; const main = async () => { const argv = getArgv(); @@ -33,16 +31,18 @@ const main = async () => { // TODO: Pass account address '', privateKey.bytes, - true + true, ); -} + + log('p2pMessageService', p2pMessageService.constructor.name); +}; main().then(() => { log('Started P2PMessageService'); -}).catch(err => { +}).catch((err) => { log(err); }); -process.on('uncaughtException', err => { +process.on('uncaughtException', (err) => { log('uncaughtException', err); }); diff --git a/packages/server/tsconfig.eslint.json b/packages/server/tsconfig.eslint.json new file mode 100644 index 00000000..25b5ba21 --- /dev/null +++ b/packages/server/tsconfig.eslint.json @@ -0,0 +1,4 @@ +{ + "extends": "./tsconfig.json", + "include": ["src/**/*.ts", "test/**/*.test.ts"] +} From 61239d3d1f7224751644d9fdb1b56716177e5a79 Mon Sep 17 00:00:00 2001 From: nabarun Date: Thu, 25 May 2023 13:05:17 +0530 Subject: [PATCH 5/5] Setup pre-commit lint --- .husky/pre-commit | 4 ++++ package.json | 6 ++++-- yarn.lock | 5 +++++ 3 files changed, 13 insertions(+), 2 deletions(-) create mode 100755 .husky/pre-commit diff --git a/.husky/pre-commit b/.husky/pre-commit new file mode 100755 index 00000000..9dcd433f --- /dev/null +++ b/.husky/pre-commit @@ -0,0 +1,4 @@ +#!/bin/sh +. "$(dirname "$0")/_/husky.sh" + +yarn lint diff --git a/package.json b/package.json index 2f24befa..0d908f14 100644 --- a/package.json +++ b/package.json @@ -8,13 +8,15 @@ "nohoist": ["**/mocha", "**/mocha/**"] }, "devDependencies": { - "lerna": "^6.6.2" + "lerna": "^6.6.2", + "husky": "^7.0.2" }, "scripts": { "lint": "lerna run lint --stream", "build:browser": "TARGET=browser lerna run build --stream --ignore @cerc-io/server", "build:node": "TARGET=node lerna run build --stream --ignore @cerc-io/example-web-app", "test:browser": "lerna run test --stream --ignore @cerc-io/server", - "test:node": "lerna run test --stream --ignore @cerc-io/example-web-app" + "test:node": "lerna run test --stream --ignore @cerc-io/example-web-app", + "prepare": "husky install" } } diff --git a/yarn.lock b/yarn.lock index a57b76fb..1a38aa0b 100644 --- a/yarn.lock +++ b/yarn.lock @@ -7760,6 +7760,11 @@ humanize-ms@^1.2.1: dependencies: ms "^2.0.0" +husky@^7.0.2: + version "7.0.4" + resolved "https://registry.yarnpkg.com/husky/-/husky-7.0.4.tgz#242048245dc49c8fb1bf0cc7cfb98dd722531535" + integrity sha512-vbaCKN2QLtP/vD4yvs6iz6hBEo6wkSzs8HpRah1Z6aGmF2KW5PdYuAd7uX5a+OyBZHBhd+TFLqgjUgytQr4RvQ== + iconv-lite@0.4.24, iconv-lite@^0.4.24: version "0.4.24" resolved "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz"