-
Notifications
You must be signed in to change notification settings - Fork 33
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Basic support for Neptune. (Will need a pool for 1 tnx per connection…
… limitation).
- Loading branch information
Jasper Blues
authored and
Jasper Blues
committed
Jan 31, 2025
1 parent
d494e52
commit 2e83e59
Showing
10 changed files
with
12,340 additions
and
7,362 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Large diffs are not rendered by default.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,91 @@ | ||
import neo4j from "neo4j-driver"; | ||
import { HttpRequest } from "@aws-sdk/protocol-http"; | ||
import { defaultProvider } from "@aws-sdk/credential-provider-node"; | ||
import { SignatureV4 } from "@aws-sdk/signature-v4"; | ||
import crypto from "@aws-crypto/sha256-js"; | ||
const { Sha256 } = crypto; | ||
import assert from "node:assert"; | ||
|
||
const region = "ap-southeast-2"; | ||
const serviceName = "neptune-db"; | ||
const host = "db-neptune-2-instance-1.cokvzz862p37.ap-southeast-2.neptune.amazonaws.com"; | ||
const port = 8182; | ||
const protocol = "bolt"; | ||
const hostPort = host + ":" + port; | ||
const url = protocol + "://" + hostPort; | ||
const createQuery = "CREATE (n:Greeting {message: 'Hello'}) RETURN ID(n)"; | ||
const readQuery = "MATCH(n:Greeting) WHERE ID(n) = $id RETURN n.message"; | ||
|
||
async function signedHeader() { | ||
const req = new HttpRequest({ | ||
method: "GET", | ||
protocol: protocol, | ||
hostname: host, | ||
port: port, | ||
// Comment out the following line if you're using an engine version older than 1.2.0.0 | ||
path: "/opencypher", | ||
headers: { | ||
host: hostPort | ||
} | ||
}); | ||
|
||
const signer = new SignatureV4({ | ||
credentials: defaultProvider(), | ||
region: region, | ||
service: serviceName, | ||
sha256: Sha256 | ||
}); | ||
|
||
return signer.sign(req, { unsignableHeaders: new Set(["x-amz-content-sha256"]) }) | ||
.then((signedRequest) => { | ||
const authInfo = { | ||
"Authorization": signedRequest.headers["authorization"], | ||
"HttpMethod": signedRequest.method, | ||
"X-Amz-Date": signedRequest.headers["x-amz-date"], | ||
"Host": signedRequest.headers["host"], | ||
"X-Amz-Security-Token": signedRequest.headers["x-amz-security-token"] | ||
}; | ||
return JSON.stringify(authInfo); | ||
}); | ||
} | ||
|
||
async function createDriver() { | ||
let authToken = { scheme: "basic", realm: "realm", principal: "username", credentials: await signedHeader() }; | ||
|
||
return neo4j.driver(url, authToken, { | ||
encrypted: "ENCRYPTION_ON", | ||
trust: "TRUST_SYSTEM_CA_SIGNED_CERTIFICATES", | ||
maxConnectionPoolSize: 1, | ||
// logging: neo4j.logging.console("debug") | ||
} | ||
); | ||
} | ||
|
||
function unmanagedTxn(driver) { | ||
const session = driver.session(); | ||
const tx = session.beginTransaction(); | ||
tx.run(createQuery) | ||
.then((res) => { | ||
const id = res.records[0].get(0); | ||
return tx.run(readQuery, { id: id }); | ||
}) | ||
.then((res) => { | ||
// All good, the transaction will be committed | ||
const msg = res.records[0].get("n.message"); | ||
assert.equal(msg, "Hello"); | ||
}) | ||
.catch(err => { | ||
// The transaction will be rolled back, now handle the error. | ||
console.log(err); | ||
}) | ||
.then(() => session.close()); | ||
} | ||
|
||
createDriver() | ||
.then((driver) => { | ||
unmanagedTxn(driver); | ||
driver.close(); | ||
}) | ||
.catch((err) => { | ||
console.log(err); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,5 +1,6 @@ | ||
export enum DatabaseType { | ||
AGENS_GRAPH = 'AGENS_GRAPH', | ||
NEO4J = 'NEO4J', | ||
POSTGRES = 'POSTGRES' | ||
POSTGRES = 'POSTGRES', | ||
NEPTUNE = 'NEPTUNE' | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,47 @@ | ||
import { ConnectionProvider } from '@/connection/ConnectionProvider'; | ||
import { Config, Driver } from 'neo4j-driver'; | ||
import { Connection } from '@/connection/Connection'; | ||
import { Neo4jConnection } from '@/connection/Neo4jConnection'; | ||
import { Neo4jResultMapper } from '@/mapper/Neo4jResultMapper'; | ||
import * as neo from 'neo4j-driver' | ||
import { DatabaseType } from '@/connection/DatabaseType'; | ||
import ShortUniqueId from 'short-unique-id'; | ||
|
||
const shortId = new ShortUniqueId({ length: 7 }); | ||
|
||
export class NeptuneConnectionProvider implements ConnectionProvider { | ||
|
||
private driver: Driver; | ||
|
||
constructor( | ||
readonly name: string, | ||
readonly type: DatabaseType, | ||
readonly host: string, | ||
readonly port: number, | ||
readonly protocol: string = 'bolt', | ||
readonly config: Config | ||
) { | ||
|
||
const url = `${this.protocol}://${this.host}:${this.port}`; | ||
const authToken = { scheme: "basic", realm: "realm", principal: "username", credentials: "" }; | ||
|
||
this.driver = neo.driver(url, authToken, { | ||
...this.config, | ||
encrypted: "ENCRYPTION_ON", | ||
trust: "TRUST_SYSTEM_CA_SIGNED_CERTIFICATES", | ||
maxConnectionPoolSize: 1, | ||
}); | ||
} | ||
|
||
async connect(): Promise<Connection> { | ||
const session = this.driver.session(); | ||
session['sessionId'] = shortId.rnd(); | ||
const connection = new Neo4jConnection(session, new Neo4jResultMapper()); | ||
return Promise.resolve(connection); | ||
} | ||
|
||
async end(): Promise<void> { | ||
return this.driver.close(); | ||
} | ||
|
||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters