UNPKG

oracledb

Version:

A Node.js module for Oracle Database access from JavaScript and TypeScript

177 lines (169 loc) 7.34 kB
// Copyright (c) 2024, 2025, Oracle and/or its affiliates. //----------------------------------------------------------------------------- // // This software is dual-licensed to you under the Universal Permissive License // (UPL) 1.0 as shown at https://oss.oracle.com/licenses/upl and Apache License // 2.0 as shown at http://www.apache.org/licenses/LICENSE-2.0. You may choose // either license. // // If you elect to accept the software under the Apache License, Version 2.0, // the following applies: // // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. // You may obtain a copy of the License at // // https://www.apache.org/licenses/LICENSE-2.0 // // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. // //----------------------------------------------------------------------------- 'use strict'; const { base } = require("../base.js"); const oracledb = require('oracledb'); const util = require('node:util'); const fs = require('fs'); const cloud_net_naming_pattern_oci = new RegExp("(?<objservername>[A-Za-z0-9._-]+)/n/" + "(?<namespace>[A-Za-z0-9._-]+)/b/" + "(?<bucketname>[A-Za-z0-9._-]+)/o/" + "(?<filename>[A-Za-z0-9._-]+)$"); // object to store module references that will be populated by init() const oci = {}; class OCIProvider extends base { constructor(provider_arg, urlExtendedPart) { super(urlExtendedPart); let match; if (provider_arg) match = provider_arg.match(cloud_net_naming_pattern_oci); if (match) { this._addParam("objservername", match.groups.objservername); this._addParam("namespace", match.groups.namespace); this._addParam("bucketname", match.groups.bucketname); this._addParam("filename", match.groups.filename); } } //--------------------------------------------------------------------------- // init() // // Require/import modules from ociobject //--------------------------------------------------------------------------- init() { oci.common = require('oci-common'); oci.objectstorage = require('oci-objectstorage'); } //--------------------------------------------------------------------------- // _streamToString() // // Converts data stored in a Readable stream to string //--------------------------------------------------------------------------- async _streamToString(stream) { const chunks = []; for await (const chunk of stream) { chunks.push(Buffer.from(chunk)); } return Buffer.concat(chunks).toString("utf-8"); } //--------------------------------------------------------------------------- // returnOCICredential() // // Returns credential to access OCI Object Store/OCI Vault on the basis of // authentication parameters given by the user. // Used in OCI/LOCALJSONFILE/OCIVAULT Config Providers //--------------------------------------------------------------------------- async returnOCICredential() { let provider = null; let auth = null; if (this.paramMap.get('authentication')) { auth = this.paramMap.get('authentication').toUpperCase(); } // authentication parameter given and its not OCI_DEFAULT if (auth && !(auth == 'OCI_DEFAULT')) { if (auth == 'OCI_INSTANCE_PRINCIPAL') { provider = await oci.common.InstancePrincipalsAuthenticationDetailsProviderBuilder().build(); } else if (auth == 'OCI_RESOURCE_PRINCIPAL') { provider = await new oci.common.ResourcePrincipalAuthenticationDetailsProvider.builder(); } else { const errmsg = util.format('OCI authentication failed: The authentication parameter value %s may be incorrect', auth); throw new Error(errmsg); } } else { // default authentication try { //authentication parameters exist in the configurationFile provider = new oci.common.ConfigFileAuthenticationDetailsProvider( this.paramMap.get("oci_profile_path"), //default path ~/.oci/config this.paramMap.get("oci_profile") ); } catch (err) { //throw error for wrong profile or wrong path if (!this.paramMap.get("oci_tenancy") || !this.paramMap.get("oci_user")) { throw (err); } // authentication parameters are directly given in the connectString const publicKey = fs.readFileSync(this.paramMap.get('oci_key_file'), { encoding: "utf8" }); let region; if (this.paramMap.get('objectservername')) region = this.retrieveRegion(this.paramMap.get('objservername')); else region = oci.common.Region[(this.paramMap.get("region").replace(/-/g, '_')).toUpperCase()]; provider = new oci.common.SimpleAuthenticationDetailsProvider( this.paramMap.get("oci_tenancy"), this.paramMap.get("oci_user"), this.paramMap.get("oci_fingerprint"), publicKey, undefined, region ); } } return provider; } //--------------------------------------------------------------------------- // returnConfig() // // Returns config stored in the OCI Object Store and // parses and gets password field stored in OCI/Azure Vault //--------------------------------------------------------------------------- async returnConfig() { this.credential = await this.returnOCICredential(); // oci object store const client_oci = new (oci.objectstorage).ObjectStorageClient({ authenticationDetailsProvider: this.credential }); const getObjectRequest = { objectName: this.paramMap.get('filename'), bucketName: this.paramMap.get('bucketname'), namespaceName: this.paramMap.get('namespace') }; const getObjectResponse = await client_oci.getObject(getObjectRequest); const resp = await this._streamToString(getObjectResponse.value); // Entire object we get from OCI Object Storage this.obj = JSON.parse(resp); const userAlias = this.paramMap.get('key'); // alias if (userAlias) { this.obj = this.obj[userAlias]; } return this.obj; } }module.exports = OCIProvider; //--------------------------------------------------------------------------- // hookFn() // hookFn will get registered to the driver while loading the plugins //--------------------------------------------------------------------------- async function hookFn(args) { const configProvider = new OCIProvider(args.provider_arg, args.urlExtendedPart); try { configProvider.init(); } catch (err) { const errmsg = util.format('Centralized Config Provider failed to load required libraries. Please install the required libraries.\n %s', err.message); throw new Error(errmsg); } try { return [await configProvider.returnConfig(), configProvider.credential]; } catch (err) { const errmsg = util.format('Failed to retrieve configuration from Centralized Configuration Provider:\n %s', err.message); throw new Error(errmsg); } } oracledb.registerConfigurationProviderHook('ociobject', hookFn);