From c3a469c04bac31a9dbdd33918b5506f47f9754ca Mon Sep 17 00:00:00 2001 From: GTFalcao Date: Thu, 24 Oct 2024 17:28:14 -0300 Subject: [PATCH 01/12] Initial AI-generated code (w/ eslint fixes) --- .../create-or-update-company.mjs | 39 ++++ .../create-or-update-custom-object.mjs | 35 +++ .../create-or-update-person.mjs | 39 ++++ .../gainsight_nxt/gainsight_nxt.app.mjs | 216 +++++++++++++++++- components/gainsight_nxt/package.json | 2 +- 5 files changed, 328 insertions(+), 3 deletions(-) create mode 100644 components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs create mode 100644 components/gainsight_nxt/actions/create-or-update-custom-object/create-or-update-custom-object.mjs create mode 100644 components/gainsight_nxt/actions/create-or-update-person/create-or-update-person.mjs diff --git a/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs b/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs new file mode 100644 index 0000000000000..ba12c78ffcfb1 --- /dev/null +++ b/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs @@ -0,0 +1,39 @@ +import gainsight_nxt from "../../gainsight_nxt.app.mjs"; + +export default { + key: "gainsight_nxt-create-or-update-company", + name: "Create or Update Company", + description: "Creates or updates a company record in Gainsight NXT. [See the documentation]().", + version: "0.0.{ts}", + type: "action", + props: { + gainsight_nxt, + companyFields: { + propDefinition: [ + gainsight_nxt, + "companyFields", + ], + }, + }, + async run({ $ }) { + // Combine companyFields array into a single object + const companyData = this.companyFields.reduce((acc, fieldStr) => { + const fieldObj = JSON.parse(fieldStr); + return { + ...acc, + ...fieldObj, + }; + }, {}); + + // Create or update the company + const result = await this.gainsight_nxt.createOrUpdateCompany(companyData); + + // Export summary + $.export( + "$summary", + `Created or updated company '${result.name}' with ID ${result.id}`, + ); + + return result; + }, +}; diff --git a/components/gainsight_nxt/actions/create-or-update-custom-object/create-or-update-custom-object.mjs b/components/gainsight_nxt/actions/create-or-update-custom-object/create-or-update-custom-object.mjs new file mode 100644 index 0000000000000..b2dfde13c2a1c --- /dev/null +++ b/components/gainsight_nxt/actions/create-or-update-custom-object/create-or-update-custom-object.mjs @@ -0,0 +1,35 @@ +import gainsight_nxt from "../../gainsight_nxt.app.mjs"; + +export default { + key: "gainsight_nxt-create-or-update-custom-object", + name: "Create or Update Custom Object", + description: "Creates or updates a custom object in Gainsight NXT. [See the documentation]()", + version: "0.0.{{ts}}", + type: "action", + props: { + gainsight_nxt, + customObjectFields: { + propDefinition: [ + "gainsight_nxt", + "customObjectFields", + ], + }, + }, + async run({ $ }) { + try { + const customObjectData = this.customObjectFields.map(JSON.parse); + const results = []; + + for (const fields of customObjectData) { + const result = await this.gainsight_nxt.createOrUpdateCustomObject(fields); + results.push(result); + } + + $.export("$summary", `Processed ${results.length} custom object(s) successfully.`); + return results; + } catch (error) { + $.export("$summary", `Failed to create or update custom objects: ${error.message}`); + throw error; + } + }, +}; diff --git a/components/gainsight_nxt/actions/create-or-update-person/create-or-update-person.mjs b/components/gainsight_nxt/actions/create-or-update-person/create-or-update-person.mjs new file mode 100644 index 0000000000000..6c41d134a43eb --- /dev/null +++ b/components/gainsight_nxt/actions/create-or-update-person/create-or-update-person.mjs @@ -0,0 +1,39 @@ +import gainsight_nxt from "../../gainsight_nxt.app.mjs"; + +export default { + key: "gainsight_nxt-create-or-update-person", + name: "Create or Update Person", + description: "Adds or updates a person's record in Gainsight NXT. [See the documentation]()", + version: "0.0.{{ts}}", + type: "action", + props: { + gainsight_nxt: { + type: "app", + app: "gainsight_nxt", + }, + personFields: { + propDefinition: [ + gainsight_nxt, + "personFields", + ], + }, + }, + async run({ $ }) { + const personData = this.personFields.reduce((acc, field) => { + const parsed = JSON.parse(field); + return { + ...acc, + ...parsed, + }; + }, {}); + + if (!personData.email) { + throw new Error("Person 'email' field is required."); + } + + const response = await this.gainsight_nxt.createOrUpdatePerson(personData); + + $.export("$summary", `Created or updated person with email ${personData.email}`); + return response; + }, +}; diff --git a/components/gainsight_nxt/gainsight_nxt.app.mjs b/components/gainsight_nxt/gainsight_nxt.app.mjs index 7e2c5ff525189..507a1e4cd28fe 100644 --- a/components/gainsight_nxt/gainsight_nxt.app.mjs +++ b/components/gainsight_nxt/gainsight_nxt.app.mjs @@ -1,11 +1,223 @@ +import { axios } from "@pipedream/platform"; + export default { type: "app", app: "gainsight_nxt", - propDefinitions: {}, + propDefinitions: { + companyFields: { + type: "string[]", + label: "Company Fields", + description: "An array of JSON strings representing company information. Include a 'name' field to identify the company.", + }, + customObjectFields: { + type: "string[]", + label: "Custom Object Fields", + description: "An array of JSON strings representing custom object elements. Include a 'name' field to identify the custom object.", + }, + personFields: { + type: "string[]", + label: "Person Fields", + description: "An array of JSON strings representing person information. Include an 'email' field to identify the person.", + }, + }, methods: { - // this.$auth contains connected account data + // This method logs the authentication keys authKeys() { console.log(Object.keys(this.$auth)); }, + // Returns the base URL for Gainsight NXT API + _baseUrl() { + return "https://api.gainsight.com/gainsight_nxt"; + }, + // Makes an HTTP request using axios + async _makeRequest(opts = {}) { + const { + $ = this, + method = "GET", + path = "/", + headers = {}, + ...otherOpts + } = opts; + return axios($, { + ...otherOpts, + method, + url: this._baseUrl() + path, + headers: { + ...headers, + "user-agent": "@PipedreamHQ/pipedream v0.1", + "Authorization": `Bearer ${this.$auth.api_token}`, + "Content-Type": "application/json", + }, + }); + }, + // Company Methods + async listCompanies(opts = {}) { + return this._makeRequest({ + path: "/companies", + method: "GET", + params: opts.params, + }); + }, + async getCompany(opts = {}) { + return this._makeRequest({ + path: `/companies/${opts.id}`, + method: "GET", + }); + }, + async createCompany(opts = {}) { + return this._makeRequest({ + path: "/companies", + method: "POST", + data: opts.data, + }); + }, + async updateCompany(opts = {}) { + return this._makeRequest({ + path: `/companies/${opts.id}`, + method: "PUT", + data: opts.data, + }); + }, + async createOrUpdateCompany(fields = {}) { + const companyData = fields; + const companyName = companyData.name; + if (!companyName) { + throw new Error("Company 'name' field is required for createOrUpdate."); + } + const response = await this.paginate(this.listCompanies, { + name: companyName, + }); + if (response.length > 0) { + const company = response[0]; + return this.updateCompany({ + id: company.id, + data: companyData, + }); + } else { + return this.createCompany({ + data: companyData, + }); + } + }, + // Custom Object Methods + async listCustomObjects(opts = {}) { + return this._makeRequest({ + path: "/custom_objects", + method: "GET", + params: opts.params, + }); + }, + async getCustomObject(opts = {}) { + return this._makeRequest({ + path: `/custom_objects/${opts.id}`, + method: "GET", + }); + }, + async createCustomObject(opts = {}) { + return this._makeRequest({ + path: "/custom_objects", + method: "POST", + data: opts.data, + }); + }, + async updateCustomObject(opts = {}) { + return this._makeRequest({ + path: `/custom_objects/${opts.id}`, + method: "PUT", + data: opts.data, + }); + }, + async createOrUpdateCustomObject(fields = {}) { + const customObjectData = fields; + const customObjectName = customObjectData.name; + if (!customObjectName) { + throw new Error("Custom Object 'name' field is required for createOrUpdate."); + } + const response = await this.paginate(this.listCustomObjects, { + name: customObjectName, + }); + if (response.length > 0) { + const customObject = response[0]; + return this.updateCustomObject({ + id: customObject.id, + data: customObjectData, + }); + } else { + return this.createCustomObject({ + data: customObjectData, + }); + } + }, + // Person Methods + async listPersons(opts = {}) { + return this._makeRequest({ + path: "/persons", + method: "GET", + params: opts.params, + }); + }, + async getPerson(opts = {}) { + return this._makeRequest({ + path: `/persons/${opts.id}`, + method: "GET", + }); + }, + async createPerson(opts = {}) { + return this._makeRequest({ + path: "/persons", + method: "POST", + data: opts.data, + }); + }, + async updatePerson(opts = {}) { + return this._makeRequest({ + path: `/persons/${opts.id}`, + method: "PUT", + data: opts.data, + }); + }, + async createOrUpdatePerson(fields = {}) { + const personData = fields; + const personEmail = personData.email; + if (!personEmail) { + throw new Error("Person 'email' field is required for createOrUpdate."); + } + const response = await this.paginate(this.listPersons, { + email: personEmail, + }); + if (response.length > 0) { + const person = response[0]; + return this.updatePerson({ + id: person.id, + data: personData, + }); + } else { + return this.createPerson({ + data: personData, + }); + } + }, + // Pagination Method + async paginate(fn, params = {}) { + let results = []; + let page = 1; + let hasMore = true; + while (hasMore) { + const response = await fn({ + params: { + ...params, + page, + }, + }); + if (response.length > 0) { + results.push(...response); + page += 1; + } else { + hasMore = false; + } + } + return results; + }, }, + version: "0.0.{ts}", }; diff --git a/components/gainsight_nxt/package.json b/components/gainsight_nxt/package.json index af6a3f4ee80c8..16cb1e5867927 100644 --- a/components/gainsight_nxt/package.json +++ b/components/gainsight_nxt/package.json @@ -12,4 +12,4 @@ "publishConfig": { "access": "public" } -} \ No newline at end of file +} From 2acaeab3ce52a3b0ffaded4db43cb95e4182fb5d Mon Sep 17 00:00:00 2001 From: GTFalcao Date: Mon, 28 Oct 2024 11:05:43 -0300 Subject: [PATCH 02/12] App/package adjustments --- .../gainsight_nxt/gainsight_nxt.app.mjs | 36 ++++++++----------- components/gainsight_nxt/package.json | 5 ++- 2 files changed, 19 insertions(+), 22 deletions(-) diff --git a/components/gainsight_nxt/gainsight_nxt.app.mjs b/components/gainsight_nxt/gainsight_nxt.app.mjs index 507a1e4cd28fe..20669bc820d8e 100644 --- a/components/gainsight_nxt/gainsight_nxt.app.mjs +++ b/components/gainsight_nxt/gainsight_nxt.app.mjs @@ -21,32 +21,26 @@ export default { }, }, methods: { - // This method logs the authentication keys - authKeys() { - console.log(Object.keys(this.$auth)); - }, - // Returns the base URL for Gainsight NXT API _baseUrl() { - return "https://api.gainsight.com/gainsight_nxt"; - }, - // Makes an HTTP request using axios - async _makeRequest(opts = {}) { - const { - $ = this, - method = "GET", - path = "/", - headers = {}, - ...otherOpts - } = opts; + return `${this.$auth.customer_domain}/v1/users/services/list`; + }, + async _makeRequest({ + $ = this, + path, + headers = {}, + ...otherOpts + } = {}) { return axios($, { ...otherOpts, - method, url: this._baseUrl() + path, headers: { - ...headers, - "user-agent": "@PipedreamHQ/pipedream v0.1", - "Authorization": `Bearer ${this.$auth.api_token}`, - "Content-Type": "application/json", + headers: { + "content-type": "application/json", + "accept": "application/json, text/plain, */*", + "accept-language": "en-GB,en-US;q=0.9,en;q=0.8", + "accesskey": `${this.gainsight_nxt.$auth.access_key}`, + ...headers, + }, }, }); }, diff --git a/components/gainsight_nxt/package.json b/components/gainsight_nxt/package.json index 16cb1e5867927..567d30336b6b0 100644 --- a/components/gainsight_nxt/package.json +++ b/components/gainsight_nxt/package.json @@ -1,6 +1,6 @@ { "name": "@pipedream/gainsight_nxt", - "version": "0.0.1", + "version": "0.1.0", "description": "Pipedream Gainsight Components", "main": "gainsight_nxt.app.mjs", "keywords": [ @@ -11,5 +11,8 @@ "author": "Pipedream (https://pipedream.com/)", "publishConfig": { "access": "public" + }, + "dependencies": { + "@pipedream/platform": "^3.0.3" } } From 17909da1e4640bced032b30afe4c5b767820acf6 Mon Sep 17 00:00:00 2001 From: GTFalcao Date: Mon, 28 Oct 2024 11:13:50 -0300 Subject: [PATCH 03/12] pnpm --- pnpm-lock.yaml | 107 +++++++++++++++++++++++++------------------------ 1 file changed, 55 insertions(+), 52 deletions(-) diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 44c19222e41ae..a996d97a3d280 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -3764,7 +3764,10 @@ importers: '@pipedream/platform': 3.0.0 components/gainsight_nxt: - specifiers: {} + specifiers: + '@pipedream/platform': ^3.0.3 + dependencies: + '@pipedream/platform': 3.0.3 components/gainsight_px: specifiers: {} @@ -13160,6 +13163,55 @@ packages: - aws-crt dev: false + /@aws-sdk/client-sso-oidc/3.600.0_tdq3komn4zwyd65w7klbptsu34: + resolution: {integrity: sha512-7+I8RWURGfzvChyNQSyj5/tKrqRbzRl7H+BnTOf/4Vsw1nFOi5ROhlhD4X/Y0QCTacxnaoNcIrqnY7uGGvVRzw==} + engines: {node: '>=16.0.0'} + dependencies: + '@aws-crypto/sha256-browser': 5.2.0 + '@aws-crypto/sha256-js': 5.2.0 + '@aws-sdk/client-sts': 3.600.0 + '@aws-sdk/core': 3.598.0 + '@aws-sdk/credential-provider-node': 3.600.0_f7n47caigsrjd2lr2szmwfuee4 + '@aws-sdk/middleware-host-header': 3.598.0 + '@aws-sdk/middleware-logger': 3.598.0 + '@aws-sdk/middleware-recursion-detection': 3.598.0 + '@aws-sdk/middleware-user-agent': 3.598.0 + '@aws-sdk/region-config-resolver': 3.598.0 + '@aws-sdk/types': 3.598.0 + '@aws-sdk/util-endpoints': 3.598.0 + '@aws-sdk/util-user-agent-browser': 3.598.0 + '@aws-sdk/util-user-agent-node': 3.598.0 + '@smithy/config-resolver': 3.0.3 + '@smithy/core': 2.2.3 + '@smithy/fetch-http-handler': 3.2.1 + '@smithy/hash-node': 3.0.2 + '@smithy/invalid-dependency': 3.0.2 + '@smithy/middleware-content-length': 3.0.2 + '@smithy/middleware-endpoint': 3.0.4 + '@smithy/middleware-retry': 3.0.6 + '@smithy/middleware-serde': 3.0.3 + '@smithy/middleware-stack': 3.0.3 + '@smithy/node-config-provider': 3.1.3 + '@smithy/node-http-handler': 3.1.2 + '@smithy/protocol-http': 4.0.3 + '@smithy/smithy-client': 3.1.6 + '@smithy/types': 3.3.0 + '@smithy/url-parser': 3.0.3 + '@smithy/util-base64': 3.0.0 + '@smithy/util-body-length-browser': 3.0.0 + '@smithy/util-body-length-node': 3.0.0 + '@smithy/util-defaults-mode-browser': 3.0.6 + '@smithy/util-defaults-mode-node': 3.0.6 + '@smithy/util-endpoints': 2.0.3 + '@smithy/util-middleware': 3.0.3 + '@smithy/util-retry': 3.0.2 + '@smithy/util-utf8': 3.0.0 + tslib: 2.6.3 + transitivePeerDependencies: + - '@aws-sdk/client-sts' + - aws-crt + dev: false + /@aws-sdk/client-sso/3.423.0: resolution: {integrity: sha512-znIufHkwhCIePgaYciIs3x/+BpzR57CZzbCKHR9+oOvGyufEPPpUT5bFLvbwTgfiVkTjuk6sG/ES3U5Bc+xtrA==} engines: {node: '>=14.0.0'} @@ -13395,7 +13447,7 @@ packages: dependencies: '@aws-crypto/sha256-browser': 5.2.0 '@aws-crypto/sha256-js': 5.2.0 - '@aws-sdk/client-sso-oidc': 3.600.0 + '@aws-sdk/client-sso-oidc': 3.600.0_tdq3komn4zwyd65w7klbptsu34 '@aws-sdk/core': 3.598.0 '@aws-sdk/credential-provider-node': 3.600.0_f7n47caigsrjd2lr2szmwfuee4 '@aws-sdk/middleware-host-header': 3.598.0 @@ -13437,55 +13489,6 @@ packages: - aws-crt dev: false - /@aws-sdk/client-sts/3.600.0_dseaa2p5u2yk67qiepewcq3hkq: - resolution: {integrity: sha512-KQG97B7LvTtTiGmjlrG1LRAY8wUvCQzrmZVV5bjrJ/1oXAU7DITYwVbSJeX9NWg6hDuSk0VE3MFwIXS2SvfLIA==} - engines: {node: '>=16.0.0'} - dependencies: - '@aws-crypto/sha256-browser': 5.2.0 - '@aws-crypto/sha256-js': 5.2.0 - '@aws-sdk/client-sso-oidc': 3.600.0 - '@aws-sdk/core': 3.598.0 - '@aws-sdk/credential-provider-node': 3.600.0_f7n47caigsrjd2lr2szmwfuee4 - '@aws-sdk/middleware-host-header': 3.598.0 - '@aws-sdk/middleware-logger': 3.598.0 - '@aws-sdk/middleware-recursion-detection': 3.598.0 - '@aws-sdk/middleware-user-agent': 3.598.0 - '@aws-sdk/region-config-resolver': 3.598.0 - '@aws-sdk/types': 3.598.0 - '@aws-sdk/util-endpoints': 3.598.0 - '@aws-sdk/util-user-agent-browser': 3.598.0 - '@aws-sdk/util-user-agent-node': 3.598.0 - '@smithy/config-resolver': 3.0.3 - '@smithy/core': 2.2.3 - '@smithy/fetch-http-handler': 3.2.1 - '@smithy/hash-node': 3.0.2 - '@smithy/invalid-dependency': 3.0.2 - '@smithy/middleware-content-length': 3.0.2 - '@smithy/middleware-endpoint': 3.0.4 - '@smithy/middleware-retry': 3.0.6 - '@smithy/middleware-serde': 3.0.3 - '@smithy/middleware-stack': 3.0.3 - '@smithy/node-config-provider': 3.1.3 - '@smithy/node-http-handler': 3.1.2 - '@smithy/protocol-http': 4.0.3 - '@smithy/smithy-client': 3.1.6 - '@smithy/types': 3.3.0 - '@smithy/url-parser': 3.0.3 - '@smithy/util-base64': 3.0.0 - '@smithy/util-body-length-browser': 3.0.0 - '@smithy/util-body-length-node': 3.0.0 - '@smithy/util-defaults-mode-browser': 3.0.6 - '@smithy/util-defaults-mode-node': 3.0.6 - '@smithy/util-endpoints': 2.0.3 - '@smithy/util-middleware': 3.0.3 - '@smithy/util-retry': 3.0.2 - '@smithy/util-utf8': 3.0.0 - tslib: 2.6.3 - transitivePeerDependencies: - - '@aws-sdk/client-sso-oidc' - - aws-crt - dev: false - /@aws-sdk/core/3.556.0: resolution: {integrity: sha512-vJaSaHw2kPQlo11j/Rzuz0gk1tEaKdz+2ser0f0qZ5vwFlANjt08m/frU17ctnVKC1s58bxpctO/1P894fHLrA==} engines: {node: '>=14.0.0'} @@ -17778,7 +17781,7 @@ packages: '@aws-sdk/client-sns': 3.423.0 '@aws-sdk/client-sqs': 3.423.0 '@aws-sdk/client-ssm': 3.423.0 - '@aws-sdk/client-sts': 3.600.0_dseaa2p5u2yk67qiepewcq3hkq + '@aws-sdk/client-sts': 3.600.0 '@aws-sdk/s3-request-presigner': 3.609.0 '@pipedream/helper_functions': 0.3.12 '@pipedream/platform': 1.6.6 From d99b6c64d5b225fbee8859ecdc031ce485d1797b Mon Sep 17 00:00:00 2001 From: GTFalcao Date: Mon, 28 Oct 2024 12:10:00 -0300 Subject: [PATCH 04/12] Create/Update company adjustments --- .../create-or-update-company.mjs | 144 +++++++++++++++--- .../gainsight_nxt/gainsight_nxt.app.mjs | 54 ++----- 2 files changed, 135 insertions(+), 63 deletions(-) diff --git a/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs b/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs index ba12c78ffcfb1..665675c3153c1 100644 --- a/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs +++ b/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs @@ -1,39 +1,143 @@ -import gainsight_nxt from "../../gainsight_nxt.app.mjs"; +import app from "../../gainsight_nxt.app.mjs"; export default { key: "gainsight_nxt-create-or-update-company", name: "Create or Update Company", - description: "Creates or updates a company record in Gainsight NXT. [See the documentation]().", + description: "Create or update a company record. [See the documentation](https://support.gainsight.com/gainsight_nxt/API_and_Developer_Docs/Company_and_Relationship_API/Company_API_Documentation#Parameters)", version: "0.0.{ts}", type: "action", props: { - gainsight_nxt, - companyFields: { - propDefinition: [ - gainsight_nxt, - "companyFields", + app, + name: { + type: "string", + label: "Name", + description: "The name of the company. If a company record with this name exists, it will be updated, otherwise a new one will be created.", + }, + industry: { + type: "string", + label: "Industry", + description: "The industry name of the company.", + optional: true, + }, + arr: { + type: "string", + label: "Anual Recurring Revenue (ARR)", + description: "The annual recurring revenue of the company, as a currency value.", + optional: true, + }, + employees: { + type: "integer", + label: "Employees", + description: "The number of employees the company has.", + optional: true, + }, + lifecycleInWeeks: { + type: "integer", + label: "Life Cycle in Weeks", + description: "The number of weeks the entire process goes through.", + optional: true, + }, + originalContractDate: { + type: "string", + label: "Original Contract Date", + description: "The date the engagement with the client started.", + optional: true, + }, + renewalDate: { + type: "string", + label: "Renewal Date", + description: "The upcoming renewal date of the contract.", + optional: true, + }, + stage: { + type: "string", + label: "Stage", + description: "The current stage of the company in the sales pipeline.", + optional: true, + options: [ + "New Customer", + "Kicked Off", + "Launched", + "Adopting", + "Will Churn", + "Churn", ], }, + status: { + type: "string", + label: "Status", + description: "The current status of the company.", + optional: true, + options: [ + "Active", + "Inactive", + "Churn", + ], + }, + csmFirstName: { + type: "string", + label: "CSM First Name", + description: "The first name of the POC of the company.", + optional: true, + }, + csmLastName: { + type: "string", + label: "CSM Last Name", + description: "The last name of the POC of the company.", + optional: true, + }, + parentCompanyName: { + type: "string", + label: "Parent Company Name", + description: "The name of the parent company.", + optional: true, + }, }, async run({ $ }) { - // Combine companyFields array into a single object - const companyData = this.companyFields.reduce((acc, fieldStr) => { - const fieldObj = JSON.parse(fieldStr); - return { - ...acc, - ...fieldObj, - }; - }, {}); + const data = { + records: [ + { + Name: this.name, + Industry: this.industry, + ARR: this.arr, + Employees: this.employees, + LifecycleInWeeks: this.lifecycleInWeeks, + OriginalContractDate: this.originalContractDate, + RenewalDate: this.renewalDate, + Stage: this.stage, + Status: this.status, + CSMFirstName: this.csmFirstName, + CSMLastName: this.csmLastName, + ParentCompanyName: this.parentCompanyName, + }, + ], + }; - // Create or update the company - const result = await this.gainsight_nxt.createOrUpdateCompany(companyData); + let summary = ""; + let result; + const updateReq = await this.app.updateCompany({ + $, + data, + }); + if (updateReq.result === true) { + result = updateReq; + summary = `Successfully updated company '${this.name}'`; + } + else { + const createReq = await this.app.createCompany({ + $, + data, + }); + result = createReq; + summary = createReq.result === true + ? `Successfully created company '${this.name}'` + : `Error when creating company '${this.name}'`; + } - // Export summary $.export( "$summary", - `Created or updated company '${result.name}' with ID ${result.id}`, + summary, ); - return result; }, }; diff --git a/components/gainsight_nxt/gainsight_nxt.app.mjs b/components/gainsight_nxt/gainsight_nxt.app.mjs index 20669bc820d8e..b2970112cad44 100644 --- a/components/gainsight_nxt/gainsight_nxt.app.mjs +++ b/components/gainsight_nxt/gainsight_nxt.app.mjs @@ -22,7 +22,7 @@ export default { }, methods: { _baseUrl() { - return `${this.$auth.customer_domain}/v1/users/services/list`; + return `${this.$auth.customer_domain}/v1`; }, async _makeRequest({ $ = this, @@ -44,54 +44,22 @@ export default { }, }); }, - // Company Methods - async listCompanies(opts = {}) { + async updateCompany(args) { return this._makeRequest({ - path: "/companies", - method: "GET", - params: opts.params, - }); - }, - async getCompany(opts = {}) { - return this._makeRequest({ - path: `/companies/${opts.id}`, - method: "GET", + path: "/data/objects/Company", + method: "PUT", + params: { + keys: "Name", + }, + ...args, }); }, - async createCompany(opts = {}) { + async createCompany(args) { return this._makeRequest({ - path: "/companies", + path: "/data/objects/Company", method: "POST", - data: opts.data, - }); - }, - async updateCompany(opts = {}) { - return this._makeRequest({ - path: `/companies/${opts.id}`, - method: "PUT", - data: opts.data, - }); - }, - async createOrUpdateCompany(fields = {}) { - const companyData = fields; - const companyName = companyData.name; - if (!companyName) { - throw new Error("Company 'name' field is required for createOrUpdate."); - } - const response = await this.paginate(this.listCompanies, { - name: companyName, + ...args, }); - if (response.length > 0) { - const company = response[0]; - return this.updateCompany({ - id: company.id, - data: companyData, - }); - } else { - return this.createCompany({ - data: companyData, - }); - } }, // Custom Object Methods async listCustomObjects(opts = {}) { From 0d15f59965bd2ba4c2d7cee1a222d59375c42cfd Mon Sep 17 00:00:00 2001 From: GTFalcao Date: Mon, 28 Oct 2024 12:21:36 -0300 Subject: [PATCH 05/12] Create/Update adjustments --- .../create-or-update-company.mjs | 18 ++++++++++-------- components/gainsight_nxt/gainsight_nxt.app.mjs | 18 +++++------------- 2 files changed, 15 insertions(+), 21 deletions(-) diff --git a/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs b/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs index 665675c3153c1..707dfbcbfb876 100644 --- a/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs +++ b/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs @@ -4,7 +4,7 @@ export default { key: "gainsight_nxt-create-or-update-company", name: "Create or Update Company", description: "Create or update a company record. [See the documentation](https://support.gainsight.com/gainsight_nxt/API_and_Developer_Docs/Company_and_Relationship_API/Company_API_Documentation#Parameters)", - version: "0.0.{ts}", + version: "0.0.{{ts}}", type: "action", props: { app, @@ -115,15 +115,17 @@ export default { let summary = ""; let result; - const updateReq = await this.app.updateCompany({ - $, - data, - }); - if (updateReq.result === true) { + try { + const updateReq = await this.app.updateCompany({ + $, + data, + }); result = updateReq; - summary = `Successfully updated company '${this.name}'`; + summary = updateReq.result === true + ? `Successfully updated company '${this.name}'` + : `Error updating company '${this.name}'`; } - else { + catch (err) { const createReq = await this.app.createCompany({ $, data, diff --git a/components/gainsight_nxt/gainsight_nxt.app.mjs b/components/gainsight_nxt/gainsight_nxt.app.mjs index b2970112cad44..0fc7e498b920b 100644 --- a/components/gainsight_nxt/gainsight_nxt.app.mjs +++ b/components/gainsight_nxt/gainsight_nxt.app.mjs @@ -4,11 +4,6 @@ export default { type: "app", app: "gainsight_nxt", propDefinitions: { - companyFields: { - type: "string[]", - label: "Company Fields", - description: "An array of JSON strings representing company information. Include a 'name' field to identify the company.", - }, customObjectFields: { type: "string[]", label: "Custom Object Fields", @@ -34,13 +29,11 @@ export default { ...otherOpts, url: this._baseUrl() + path, headers: { - headers: { - "content-type": "application/json", - "accept": "application/json, text/plain, */*", - "accept-language": "en-GB,en-US;q=0.9,en;q=0.8", - "accesskey": `${this.gainsight_nxt.$auth.access_key}`, - ...headers, - }, + "content-type": "application/json", + "accept": "application/json, text/plain, */*", + "accept-language": "en-GB,en-US;q=0.9,en;q=0.8", + "accesskey": `${this.$auth.access_key}`, + ...headers, }, }); }, @@ -181,5 +174,4 @@ export default { return results; }, }, - version: "0.0.{ts}", }; From 7770034fbab1cbe97f1b7c9ae22751a6151b46a5 Mon Sep 17 00:00:00 2001 From: GTFalcao Date: Mon, 28 Oct 2024 13:24:00 -0300 Subject: [PATCH 06/12] Create/update person adjustments --- .../create-or-update-person.mjs | 72 +++++++---- .../gainsight_nxt/gainsight_nxt.app.mjs | 118 +----------------- 2 files changed, 51 insertions(+), 139 deletions(-) diff --git a/components/gainsight_nxt/actions/create-or-update-person/create-or-update-person.mjs b/components/gainsight_nxt/actions/create-or-update-person/create-or-update-person.mjs index 6c41d134a43eb..735ad68a78170 100644 --- a/components/gainsight_nxt/actions/create-or-update-person/create-or-update-person.mjs +++ b/components/gainsight_nxt/actions/create-or-update-person/create-or-update-person.mjs @@ -1,39 +1,63 @@ -import gainsight_nxt from "../../gainsight_nxt.app.mjs"; +import app from "../../gainsight_nxt.app.mjs"; export default { key: "gainsight_nxt-create-or-update-person", name: "Create or Update Person", - description: "Adds or updates a person's record in Gainsight NXT. [See the documentation]()", + description: "Create or update a person's record. [See the documentation](https://support.gainsight.com/gainsight_nxt/API_and_Developer_Docs/Person_API/People_API_Documentation#Person)", version: "0.0.{{ts}}", type: "action", props: { - gainsight_nxt: { - type: "app", - app: "gainsight_nxt", + app, + email: { + type: "string", + label: "Email", + description: "The email address of the person. If a record with this email exists, it will be updated, otherwise a new one will be created.", }, - personFields: { - propDefinition: [ - gainsight_nxt, - "personFields", - ], + firstName: { + type: "string", + label: "First Name", + description: "The first name of the person.", + optional: true, + }, + lastName: { + type: "string", + label: "Last Name", + description: "The last name of the person.", + optional: true, + }, + linkedinUrl: { + type: "string", + label: "LinkedIn URL", + description: "The LinkedIn URL of the person.", + optional: true, + }, + location: { + type: "string", + label: "Location", + description: "The location of the person.", + optional: true, + }, + additionalFields: { + type: "object", + label: "Additional Fields", + description: "Additional fields to include in the request body. [See the documentation](https://support.gainsight.com/gainsight_nxt/API_and_Developer_Docs/Person_API/People_API_Documentation#Person) for all available fields.", + optional: true, }, }, async run({ $ }) { - const personData = this.personFields.reduce((acc, field) => { - const parsed = JSON.parse(field); - return { - ...acc, - ...parsed, - }; - }, {}); - - if (!personData.email) { - throw new Error("Person 'email' field is required."); - } - - const response = await this.gainsight_nxt.createOrUpdatePerson(personData); + const response = await this.app.createOrUpdatePerson({ + $, + data: { + Email: this.email, + FirstName: this.firstName, + LastName: this.lastName, + LinkedinUrl: this.linkedinUrl, + Location: this.location, + ...this.additionalFields, + }, + }); - $.export("$summary", `Created or updated person with email ${personData.email}`); + $.export("$summary", `Successfully upserted person with email ${this.email}`); return response; }, }; diff --git a/components/gainsight_nxt/gainsight_nxt.app.mjs b/components/gainsight_nxt/gainsight_nxt.app.mjs index 0fc7e498b920b..1b89370e8a09d 100644 --- a/components/gainsight_nxt/gainsight_nxt.app.mjs +++ b/components/gainsight_nxt/gainsight_nxt.app.mjs @@ -54,124 +54,12 @@ export default { ...args, }); }, - // Custom Object Methods - async listCustomObjects(opts = {}) { + async createOrUpdatePerson(args) { return this._makeRequest({ - path: "/custom_objects", - method: "GET", - params: opts.params, - }); - }, - async getCustomObject(opts = {}) { - return this._makeRequest({ - path: `/custom_objects/${opts.id}`, - method: "GET", - }); - }, - async createCustomObject(opts = {}) { - return this._makeRequest({ - path: "/custom_objects", - method: "POST", - data: opts.data, - }); - }, - async updateCustomObject(opts = {}) { - return this._makeRequest({ - path: `/custom_objects/${opts.id}`, - method: "PUT", - data: opts.data, - }); - }, - async createOrUpdateCustomObject(fields = {}) { - const customObjectData = fields; - const customObjectName = customObjectData.name; - if (!customObjectName) { - throw new Error("Custom Object 'name' field is required for createOrUpdate."); - } - const response = await this.paginate(this.listCustomObjects, { - name: customObjectName, - }); - if (response.length > 0) { - const customObject = response[0]; - return this.updateCustomObject({ - id: customObject.id, - data: customObjectData, - }); - } else { - return this.createCustomObject({ - data: customObjectData, - }); - } - }, - // Person Methods - async listPersons(opts = {}) { - return this._makeRequest({ - path: "/persons", - method: "GET", - params: opts.params, - }); - }, - async getPerson(opts = {}) { - return this._makeRequest({ - path: `/persons/${opts.id}`, - method: "GET", - }); - }, - async createPerson(opts = {}) { - return this._makeRequest({ - path: "/persons", - method: "POST", - data: opts.data, - }); - }, - async updatePerson(opts = {}) { - return this._makeRequest({ - path: `/persons/${opts.id}`, + path: "/peoplemgmt/v1.0/people", method: "PUT", - data: opts.data, - }); - }, - async createOrUpdatePerson(fields = {}) { - const personData = fields; - const personEmail = personData.email; - if (!personEmail) { - throw new Error("Person 'email' field is required for createOrUpdate."); - } - const response = await this.paginate(this.listPersons, { - email: personEmail, + ...args, }); - if (response.length > 0) { - const person = response[0]; - return this.updatePerson({ - id: person.id, - data: personData, - }); - } else { - return this.createPerson({ - data: personData, - }); - } - }, - // Pagination Method - async paginate(fn, params = {}) { - let results = []; - let page = 1; - let hasMore = true; - while (hasMore) { - const response = await fn({ - params: { - ...params, - page, - }, - }); - if (response.length > 0) { - results.push(...response); - page += 1; - } else { - hasMore = false; - } - } - return results; }, }, }; From 87ccc95e19e90fd7e9e82a2b734b6546f648ea68 Mon Sep 17 00:00:00 2001 From: GTFalcao Date: Mon, 28 Oct 2024 18:27:59 -0300 Subject: [PATCH 07/12] Create/Update Custom Object + improvements --- .../create-or-update-company.mjs | 2 +- .../create-or-update-custom-object.mjs | 71 ++++++++++++++----- .../gainsight_nxt/gainsight_nxt.app.mjs | 45 +++++++++--- 3 files changed, 89 insertions(+), 29 deletions(-) diff --git a/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs b/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs index 707dfbcbfb876..c3657ae2ea30b 100644 --- a/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs +++ b/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs @@ -133,7 +133,7 @@ export default { result = createReq; summary = createReq.result === true ? `Successfully created company '${this.name}'` - : `Error when creating company '${this.name}'`; + : `Error creating company '${this.name}'`; } $.export( diff --git a/components/gainsight_nxt/actions/create-or-update-custom-object/create-or-update-custom-object.mjs b/components/gainsight_nxt/actions/create-or-update-custom-object/create-or-update-custom-object.mjs index b2dfde13c2a1c..05db519404a17 100644 --- a/components/gainsight_nxt/actions/create-or-update-custom-object/create-or-update-custom-object.mjs +++ b/components/gainsight_nxt/actions/create-or-update-custom-object/create-or-update-custom-object.mjs @@ -1,35 +1,68 @@ -import gainsight_nxt from "../../gainsight_nxt.app.mjs"; +import app from "../../gainsight_nxt.app.mjs"; export default { key: "gainsight_nxt-create-or-update-custom-object", name: "Create or Update Custom Object", - description: "Creates or updates a custom object in Gainsight NXT. [See the documentation]()", + description: "Create or update a custom object record. [See the documentation](https://support.gainsight.com/gainsight_nxt/API_and_Developer_Docs/Custom_Object_API/Gainsight_Custom_Object_API_Documentation#Insert_API)", version: "0.0.{{ts}}", type: "action", props: { - gainsight_nxt, - customObjectFields: { + app, + objectName: { propDefinition: [ - "gainsight_nxt", - "customObjectFields", + app, + "objectName", ], }, + fields: { + type: "string[]", + label: "Key Field(s)", + description: "The field(s) which identify this object (max 3), e.g. `fieldName1`. If a record with the same key field(s) exists, it will be updated, otherwise a new one will be created.", + }, + fieldValues: { + type: "object", + label: "Field Values", + description: "The record data to create or update, as key-value pairs.", + }, }, async run({ $ }) { - try { - const customObjectData = this.customObjectFields.map(JSON.parse); - const results = []; - - for (const fields of customObjectData) { - const result = await this.gainsight_nxt.createOrUpdateCustomObject(fields); - results.push(result); - } + const { objectName } = this; + const data = { + records: [ + this.fieldValues, + ], + }; - $.export("$summary", `Processed ${results.length} custom object(s) successfully.`); - return results; - } catch (error) { - $.export("$summary", `Failed to create or update custom objects: ${error.message}`); - throw error; + let summary = ""; + let result; + try { + result = await this.app.updateCustomObject({ + $, + objectName, + data, + params: { + keys: this.fields.join?.() ?? this.fields, + }, + }); + summary = result.result === true + ? `Successfully updated custom object ${objectName}` + : `Error updating custom object ${objectName}`; } + catch (err) { + result = await this.app.createCustomObject({ + $, + objectName, + data, + }); + summary = result.result === true + ? `Successfully created custom object ${objectName}` + : `Error creating custom object ${objectName}`; + } + + $.export( + "$summary", + summary, + ); + return result; }, }; diff --git a/components/gainsight_nxt/gainsight_nxt.app.mjs b/components/gainsight_nxt/gainsight_nxt.app.mjs index 1b89370e8a09d..478d5cb3fd363 100644 --- a/components/gainsight_nxt/gainsight_nxt.app.mjs +++ b/components/gainsight_nxt/gainsight_nxt.app.mjs @@ -4,15 +4,19 @@ export default { type: "app", app: "gainsight_nxt", propDefinitions: { - customObjectFields: { - type: "string[]", - label: "Custom Object Fields", - description: "An array of JSON strings representing custom object elements. Include a 'name' field to identify the custom object.", - }, - personFields: { - type: "string[]", - label: "Person Fields", - description: "An array of JSON strings representing person information. Include an 'email' field to identify the person.", + objectName: { + type: "string", + label: "Custom Object", + description: "The name of the custom object.", + async options() { + const { data } = await this.listCustomObjects(); + return data/*?.filter?.((obj) => obj.objectType === "CUSTOM")*/.map(( { + label, objectName, + }) => ({ + label, + value: objectName, + })); + }, }, }, methods: { @@ -61,5 +65,28 @@ export default { ...args, }); }, + async listCustomObjects() { + return this._makeRequest({ + path: "/meta/services/objects/list", + }); + }, + async updateCustomObject({ + objectName, ...args + }) { + return this._makeRequest({ + path: `/data/objects/${objectName}`, + method: "PUT", + ...args, + }); + }, + async createCustomObject({ + objectName, ...args + }) { + return this._makeRequest({ + path: `/data/objects/${objectName}`, + method: "POST", + ...args, + }); + }, }, }; From 9b344527f71fc27749e11ff566bae9db17a47dcb Mon Sep 17 00:00:00 2001 From: GTFalcao Date: Mon, 28 Oct 2024 18:49:04 -0300 Subject: [PATCH 08/12] Version numbers --- .../create-or-update-company/create-or-update-company.mjs | 2 +- .../create-or-update-custom-object.mjs | 2 +- .../actions/create-or-update-person/create-or-update-person.mjs | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs b/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs index c3657ae2ea30b..43550a4cedf8b 100644 --- a/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs +++ b/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs @@ -4,7 +4,7 @@ export default { key: "gainsight_nxt-create-or-update-company", name: "Create or Update Company", description: "Create or update a company record. [See the documentation](https://support.gainsight.com/gainsight_nxt/API_and_Developer_Docs/Company_and_Relationship_API/Company_API_Documentation#Parameters)", - version: "0.0.{{ts}}", + version: "0.0.1", type: "action", props: { app, diff --git a/components/gainsight_nxt/actions/create-or-update-custom-object/create-or-update-custom-object.mjs b/components/gainsight_nxt/actions/create-or-update-custom-object/create-or-update-custom-object.mjs index 05db519404a17..9c9857f5c77bf 100644 --- a/components/gainsight_nxt/actions/create-or-update-custom-object/create-or-update-custom-object.mjs +++ b/components/gainsight_nxt/actions/create-or-update-custom-object/create-or-update-custom-object.mjs @@ -4,7 +4,7 @@ export default { key: "gainsight_nxt-create-or-update-custom-object", name: "Create or Update Custom Object", description: "Create or update a custom object record. [See the documentation](https://support.gainsight.com/gainsight_nxt/API_and_Developer_Docs/Custom_Object_API/Gainsight_Custom_Object_API_Documentation#Insert_API)", - version: "0.0.{{ts}}", + version: "0.0.1", type: "action", props: { app, diff --git a/components/gainsight_nxt/actions/create-or-update-person/create-or-update-person.mjs b/components/gainsight_nxt/actions/create-or-update-person/create-or-update-person.mjs index 735ad68a78170..64042f8158fb2 100644 --- a/components/gainsight_nxt/actions/create-or-update-person/create-or-update-person.mjs +++ b/components/gainsight_nxt/actions/create-or-update-person/create-or-update-person.mjs @@ -4,7 +4,7 @@ export default { key: "gainsight_nxt-create-or-update-person", name: "Create or Update Person", description: "Create or update a person's record. [See the documentation](https://support.gainsight.com/gainsight_nxt/API_and_Developer_Docs/Person_API/People_API_Documentation#Person)", - version: "0.0.{{ts}}", + version: "0.0.1", type: "action", props: { app, From c5a99d48bfd07ffef9a3a85a56ee5786b0b660a9 Mon Sep 17 00:00:00 2001 From: GTFalcao Date: Tue, 29 Oct 2024 14:46:10 -0300 Subject: [PATCH 09/12] Fixes --- .../create-or-update-company/create-or-update-company.mjs | 6 +++--- components/gainsight_nxt/gainsight_nxt.app.mjs | 2 +- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs b/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs index 43550a4cedf8b..5cad58c2f169f 100644 --- a/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs +++ b/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs @@ -21,7 +21,7 @@ export default { }, arr: { type: "string", - label: "Anual Recurring Revenue (ARR)", + label: "Annual Recurring Revenue (ARR)", description: "The annual recurring revenue of the company, as a currency value.", optional: true, }, @@ -40,13 +40,13 @@ export default { originalContractDate: { type: "string", label: "Original Contract Date", - description: "The date the engagement with the client started.", + description: "The date the engagement with the client started, in `YYYY-MM-DD` format.", optional: true, }, renewalDate: { type: "string", label: "Renewal Date", - description: "The upcoming renewal date of the contract.", + description: "The upcoming renewal date of the contract, in `YYYY-MM-DD` format.", optional: true, }, stage: { diff --git a/components/gainsight_nxt/gainsight_nxt.app.mjs b/components/gainsight_nxt/gainsight_nxt.app.mjs index 478d5cb3fd363..714b064d5b524 100644 --- a/components/gainsight_nxt/gainsight_nxt.app.mjs +++ b/components/gainsight_nxt/gainsight_nxt.app.mjs @@ -10,7 +10,7 @@ export default { description: "The name of the custom object.", async options() { const { data } = await this.listCustomObjects(); - return data/*?.filter?.((obj) => obj.objectType === "CUSTOM")*/.map(( { + return data.map(( { label, objectName, }) => ({ label, From 3c548be88224d00c81aa21f85d8e432c3f43d04b Mon Sep 17 00:00:00 2001 From: GTFalcao Date: Thu, 31 Oct 2024 16:07:12 -0300 Subject: [PATCH 10/12] Removing CSM props and adding "additional options" --- .../create-or-update-company.mjs | 26 +++++-------------- components/gainsight_nxt/common/utils.mjs | 22 ++++++++++++++++ 2 files changed, 29 insertions(+), 19 deletions(-) create mode 100644 components/gainsight_nxt/common/utils.mjs diff --git a/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs b/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs index 5cad58c2f169f..9e0f536672c31 100644 --- a/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs +++ b/components/gainsight_nxt/actions/create-or-update-company/create-or-update-company.mjs @@ -1,3 +1,4 @@ +import { parseObjectEntries } from "../../common/utils.mjs"; import app from "../../gainsight_nxt.app.mjs"; export default { @@ -74,22 +75,11 @@ export default { "Churn", ], }, - csmFirstName: { - type: "string", - label: "CSM First Name", - description: "The first name of the POC of the company.", - optional: true, - }, - csmLastName: { - type: "string", - label: "CSM Last Name", - description: "The last name of the POC of the company.", - optional: true, - }, - parentCompanyName: { - type: "string", - label: "Parent Company Name", - description: "The name of the parent company.", + additionalOptions: { + type: "object", + label: "Additional Options", + description: + "Additional parameters to send in the request. [See the documentation](https://support.gainsight.com/gainsight_nxt/API_and_Developer_Docs/Company_and_Relationship_API/Company_API_Documentation#Parameters) for available parameters. Values will be parsed as JSON where applicable.", optional: true, }, }, @@ -106,9 +96,7 @@ export default { RenewalDate: this.renewalDate, Stage: this.stage, Status: this.status, - CSMFirstName: this.csmFirstName, - CSMLastName: this.csmLastName, - ParentCompanyName: this.parentCompanyName, + ...(this.additionalOptions && parseObjectEntries(this.additionalOptions)), }, ], }; diff --git a/components/gainsight_nxt/common/utils.mjs b/components/gainsight_nxt/common/utils.mjs new file mode 100644 index 0000000000000..9c3cdbf569744 --- /dev/null +++ b/components/gainsight_nxt/common/utils.mjs @@ -0,0 +1,22 @@ +function optionalParseAsJSON(value) { + try { + return JSON.parse(value); + } catch (e) { + return value; + } +} + +export function parseObjectEntries(value) { + const obj = typeof value === "string" + ? JSON.parse(value) + : value; + return Object.fromEntries( + Object.entries(obj).map(([ + key, + value, + ]) => [ + key, + optionalParseAsJSON(value), + ]), + ); +} From 361a5275499c098f65293b065c4dcb87dce6b448 Mon Sep 17 00:00:00 2001 From: GTFalcao Date: Thu, 31 Oct 2024 16:26:28 -0300 Subject: [PATCH 11/12] Readding 'custom' object filter --- components/gainsight_nxt/gainsight_nxt.app.mjs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/components/gainsight_nxt/gainsight_nxt.app.mjs b/components/gainsight_nxt/gainsight_nxt.app.mjs index 714b064d5b524..aef6c222e128a 100644 --- a/components/gainsight_nxt/gainsight_nxt.app.mjs +++ b/components/gainsight_nxt/gainsight_nxt.app.mjs @@ -10,7 +10,7 @@ export default { description: "The name of the custom object.", async options() { const { data } = await this.listCustomObjects(); - return data.map(( { + return data?.filter?.((obj) => obj.objectType === "CUSTOM").map(( { label, objectName, }) => ({ label, From d8408200da66b283110de97c7bf8dc2f91cab7d2 Mon Sep 17 00:00:00 2001 From: GTFalcao Date: Wed, 6 Nov 2024 01:10:34 -0300 Subject: [PATCH 12/12] Adding info box --- .../create-or-update-custom-object.mjs | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/components/gainsight_nxt/actions/create-or-update-custom-object/create-or-update-custom-object.mjs b/components/gainsight_nxt/actions/create-or-update-custom-object/create-or-update-custom-object.mjs index 9c9857f5c77bf..f097bcae5e394 100644 --- a/components/gainsight_nxt/actions/create-or-update-custom-object/create-or-update-custom-object.mjs +++ b/components/gainsight_nxt/actions/create-or-update-custom-object/create-or-update-custom-object.mjs @@ -14,6 +14,11 @@ export default { "objectName", ], }, + infoBox: { + type: "alert", + alertType: "info", + content: "Custom object fields may be suffixed with `__gc`, e.g. if you've named your field \"Object Name\", its key would be `Object_Name__gc`. Check the object configuration in the Gainsight platform for the correct field names.", + }, fields: { type: "string[]", label: "Key Field(s)",