Skip to content

Commit 8cdf895

Browse files
Quickbooks Usability Audit (#14712)
* refactoring * quickbooks_sandbox components * update update-item * minor updates * add async options * refactor props * pnpm-lock.yaml * update versions * fixes * fix path * add get-payment * wip * updates * pnpm-lock.yaml * fixes * Require Vendor ID * updates * versions * updates --------- Co-authored-by: Leo Vu <vunguyenhung@outlook.com>
1 parent 330ef84 commit 8cdf895

File tree

86 files changed

+2381
-2205
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

86 files changed

+2381
-2205
lines changed

components/quickbooks/actions/create-ap-aging-report/create-ap-aging-report.mjs

+1-1
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ export default {
55
key: "quickbooks-create-ap-aging-report",
66
name: "Create AP Aging Detail Report",
77
description: "Creates an AP aging report in Quickbooks Online. [See the documentation](https://developer.intuit.com/app/developer/qbo/docs/api/accounting/all-entities/apagingdetail#query-a-report)",
8-
version: "0.0.1",
8+
version: "0.0.2",
99
type: "action",
1010
props: {
1111
quickbooks,

components/quickbooks/actions/create-bill/create-bill.mjs

+82-37
Original file line numberDiff line numberDiff line change
@@ -1,84 +1,129 @@
11
import { ConfigurationError } from "@pipedream/platform";
22
import quickbooks from "../../quickbooks.app.mjs";
3+
import { parseLineItems } from "../../common/utils.mjs";
34

45
export default {
56
key: "quickbooks-create-bill",
67
name: "Create Bill",
7-
description: "Creates a bill. [See docs here](https://developer.intuit.com/app/developer/qbo/docs/api/accounting/all-entities/bill#create-a-bill)",
8-
version: "0.1.6",
8+
description: "Creates a bill. [See the documentation](https://developer.intuit.com/app/developer/qbo/docs/api/accounting/all-entities/bill#create-a-bill)",
9+
version: "0.1.7",
910
type: "action",
1011
props: {
1112
quickbooks,
1213
vendorRefValue: {
13-
label: "Vendor Ref Value",
14-
type: "string",
15-
description: "Reference to the vendor for this transaction. Query the Vendor name list resource to determine the appropriate Vendor object for this reference. Use `Vendor.Id` from that object for `VendorRef.value`.",
16-
},
17-
lineItems: {
18-
description: "Individual line items of a transaction. Valid Line types include: `ItemBasedExpenseLine` and `AccountBasedExpenseLine`. One minimum line item required for the request to succeed. E.g `[ { \"DetailType\": \"AccountBasedExpenseLineDetail\", \"Amount\": 200.0, \"AccountBasedExpenseLineDetail\": { \"AccountRef\": { \"value\": \"1\" } } } ]`",
1914
propDefinition: [
2015
quickbooks,
21-
"lineItems",
16+
"vendorIds",
2217
],
23-
},
24-
vendorRefName: {
25-
label: "Vendor Reference Name",
2618
type: "string",
27-
description: "Reference to the vendor for this transaction. Query the Vendor name list resource to determine the appropriate Vendor object for this reference. Use `Vendor.Name` from that object for `VendorRef.name`.",
28-
optional: true,
19+
label: "Vendor ID",
20+
description: "Reference to the vendor for this transaction",
21+
optional: false,
2922
},
3023
currencyRefValue: {
3124
propDefinition: [
3225
quickbooks,
33-
"currencyRefValue",
26+
"currency",
3427
],
3528
},
36-
currencyRefName: {
29+
lineItemsAsObjects: {
3730
propDefinition: [
3831
quickbooks,
39-
"currencyRefName",
32+
"lineItemsAsObjects",
4033
],
34+
reloadProps: true,
4135
},
42-
minorVersion: {
43-
propDefinition: [
44-
quickbooks,
45-
"minorVersion",
46-
],
36+
},
37+
async additionalProps() {
38+
const props = {};
39+
if (this.lineItemsAsObjects) {
40+
props.lineItems = {
41+
type: "string[]",
42+
label: "Line Items",
43+
description: "Line items of a bill. Set DetailType to `AccountBasedExpenseLineDetail`. Example: `{ \"DetailType\": \"AccountBasedExpenseLineDetail\", \"Amount\": 100.0, \"AccountBasedExpenseLineDetail\": { \"AccountRef\": { \"name\": \"Advertising\", \"value\": \"1\" } } }`",
44+
};
45+
return props;
46+
}
47+
props.numLineItems = {
48+
type: "integer",
49+
label: "Number of Line Items",
50+
description: "The number of line items to enter",
51+
reloadProps: true,
52+
};
53+
if (!this.numLineItems) {
54+
return props;
55+
}
56+
for (let i = 1; i <= this.numLineItems; i++) {
57+
props[`account_${i}`] = {
58+
type: "string",
59+
label: `Line ${i} - Account ID`,
60+
options: async ({ page }) => {
61+
return this.quickbooks.getPropOptions({
62+
page,
63+
resource: "Account",
64+
mapper: ({
65+
Id: value, Name: label,
66+
}) => ({
67+
value,
68+
label,
69+
}),
70+
});
71+
},
72+
};
73+
props[`amount_${i}`] = {
74+
type: "string",
75+
label: `Line ${i} - Amount`,
76+
};
77+
}
78+
return props;
79+
},
80+
methods: {
81+
buildLineItems() {
82+
const lineItems = [];
83+
for (let i = 1; i <= this.numLineItems; i++) {
84+
lineItems.push({
85+
DetailType: "AccountBasedExpenseLineDetail",
86+
Amount: this[`amount_${i}`],
87+
AccountBasedExpenseLineDetail: {
88+
AccountRef: {
89+
value: this[`account_${i}`],
90+
},
91+
},
92+
});
93+
}
94+
return lineItems;
4795
},
4896
},
4997
async run({ $ }) {
50-
if (!this.vendorRefValue || !this.lineItems) {
98+
if (!this.vendorRefValue || (!this.numLineItems && !this.lineItemsAsObjects)) {
5199
throw new ConfigurationError("Must provide vendorRefValue, and lineItems parameters.");
52100
}
53101

54-
try {
55-
this.lineItems = this.lineItems.map((lineItem) => typeof lineItem === "string"
56-
? JSON.parse(lineItem)
57-
: lineItem);
58-
} catch (error) {
59-
throw new ConfigurationError(`We got an error trying to parse the LineItems. Error: ${error}`);
60-
}
102+
const lines = this.lineItemsAsObjects
103+
? parseLineItems(this.lineItems)
104+
: this.buildLineItems();
105+
106+
lines.forEach((line) => {
107+
if (line.DetailType !== "AccountBasedExpenseLineDetail") {
108+
throw new ConfigurationError("Line Item DetailType must be `AccountBasedExpenseLineDetail`");
109+
}
110+
});
61111

62112
const response = await this.quickbooks.createBill({
63113
$,
64114
data: {
65115
VendorRef: {
66116
value: this.vendorRefValue,
67-
name: this.vendorRefName,
68117
},
69-
Line: this.lineItems,
118+
Line: lines,
70119
CurrencyRef: {
71120
value: this.currencyRefValue,
72-
name: this.currencyRefName,
73121
},
74122
},
75-
params: {
76-
minorversion: this.minorVersion,
77-
},
78123
});
79124

80125
if (response) {
81-
$.export("summary", `Successfully created bill with id ${response.Bill.Id}`);
126+
$.export("summary", `Successfully created bill with ID ${response.Bill.Id}`);
82127
}
83128

84129
return response;

components/quickbooks/actions/create-customer/create-customer.mjs

+3-12
Original file line numberDiff line numberDiff line change
@@ -4,8 +4,8 @@ import quickbooks from "../../quickbooks.app.mjs";
44
export default {
55
key: "quickbooks-create-customer",
66
name: "Create Customer",
7-
description: "Creates a customer. [See docs here](https://developer.intuit.com/app/developer/qbo/docs/api/accounting/all-entities/customer#create-a-customer)",
8-
version: "0.1.6",
7+
description: "Creates a customer. [See the documentation](https://developer.intuit.com/app/developer/qbo/docs/api/accounting/all-entities/customer#create-a-customer)",
8+
version: "0.1.7",
99
type: "action",
1010
props: {
1111
quickbooks,
@@ -45,12 +45,6 @@ export default {
4545
"suffix",
4646
],
4747
},
48-
minorVersion: {
49-
propDefinition: [
50-
quickbooks,
51-
"minorVersion",
52-
],
53-
},
5448
},
5549
async run({ $ }) {
5650
if (
@@ -70,13 +64,10 @@ export default {
7064
FamilyName: this.familyName,
7165
GivenName: this.givenName,
7266
},
73-
params: {
74-
minorversion: this.minorVersion,
75-
},
7667
});
7768

7869
if (response) {
79-
$.export("summary", `Successfully created customer with id ${response.Customer.Id}`);
70+
$.export("summary", `Successfully created customer with ID ${response.Customer.Id}`);
8071
}
8172

8273
return response;

components/quickbooks/actions/create-invoice/create-invoice.mjs

+79-37
Original file line numberDiff line numberDiff line change
@@ -1,83 +1,125 @@
11
import { ConfigurationError } from "@pipedream/platform";
22
import quickbooks from "../../quickbooks.app.mjs";
3+
import { parseLineItems } from "../../common/utils.mjs";
34

45
export default {
56
key: "quickbooks-create-invoice",
67
name: "Create Invoice",
7-
description: "Creates an invoice. [See docs here](https://developer.intuit.com/app/developer/qbo/docs/api/accounting/all-entities/invoice#create-an-invoice)",
8-
version: "0.1.6",
8+
description: "Creates an invoice. [See the documentation](https://developer.intuit.com/app/developer/qbo/docs/api/accounting/all-entities/invoice#create-an-invoice)",
9+
version: "0.1.7",
910
type: "action",
1011
props: {
1112
quickbooks,
12-
lineItems: {
13-
propDefinition: [
14-
quickbooks,
15-
"lineItems",
16-
],
17-
},
1813
customerRefValue: {
19-
label: "Customer Reference Value",
20-
type: "string",
21-
description: "Reference to a customer or job. Query the Customer name list resource to determine the appropriate Customer object for this reference. Use `Customer.Id` from that object for `CustomerRef.value`.",
22-
},
23-
customerRefName: {
2414
propDefinition: [
2515
quickbooks,
26-
"customerRefName",
16+
"customer",
2717
],
2818
},
2919
currencyRefValue: {
3020
propDefinition: [
3121
quickbooks,
32-
"currencyRefValue",
22+
"currency",
3323
],
3424
},
35-
currencyRefName: {
25+
lineItemsAsObjects: {
3626
propDefinition: [
3727
quickbooks,
38-
"currencyRefName",
28+
"lineItemsAsObjects",
3929
],
30+
reloadProps: true,
4031
},
41-
minorVersion: {
42-
propDefinition: [
43-
quickbooks,
44-
"minorVersion",
45-
],
32+
},
33+
async additionalProps() {
34+
const props = {};
35+
if (this.lineItemsAsObjects) {
36+
props.lineItems = {
37+
type: "string[]",
38+
label: "Line Items",
39+
description: "Line items of an invoice. Set DetailType to `SalesItemLineDetail`, `GroupLineDetail`, or `DescriptionOnly`. Example: `{ \"DetailType\": \"SalesItemLineDetail\", \"Amount\": 100.0, \"SalesItemLineDetail\": { \"ItemRef\": { \"name\": \"Services\", \"value\": \"1\" } } }`",
40+
};
41+
return props;
42+
}
43+
props.numLineItems = {
44+
type: "integer",
45+
label: "Number of Line Items",
46+
description: "The number of line items to enter",
47+
reloadProps: true,
48+
};
49+
if (!this.numLineItems) {
50+
return props;
51+
}
52+
for (let i = 1; i <= this.numLineItems; i++) {
53+
props[`item_${i}`] = {
54+
type: "string",
55+
label: `Line ${i} - Item ID`,
56+
options: async ({ page }) => {
57+
return this.quickbooks.getPropOptions({
58+
page,
59+
resource: "Item",
60+
mapper: ({
61+
Id: value, Name: label,
62+
}) => ({
63+
value,
64+
label,
65+
}),
66+
});
67+
},
68+
};
69+
props[`amount_${i}`] = {
70+
type: "string",
71+
label: `Line ${i} - Amount`,
72+
};
73+
}
74+
return props;
75+
},
76+
methods: {
77+
buildLineItems() {
78+
const lineItems = [];
79+
for (let i = 1; i <= this.numLineItems; i++) {
80+
lineItems.push({
81+
DetailType: "SalesItemLineDetail",
82+
Amount: this[`amount_${i}`],
83+
SalesItemLineDetail: {
84+
ItemRef: {
85+
value: this[`item_${i}`],
86+
},
87+
},
88+
});
89+
}
90+
return lineItems;
4691
},
4792
},
4893
async run({ $ }) {
49-
if (!this.lineItems || !this.customerRefValue) {
94+
if ((!this.numLineItems && !this.lineItemsAsObjects) || !this.customerRefValue) {
5095
throw new ConfigurationError("Must provide lineItems, and customerRefValue parameters.");
5196
}
5297

53-
try {
54-
this.lineItems = this.lineItems.map((lineItem) => typeof lineItem === "string"
55-
? JSON.parse(lineItem)
56-
: lineItem);
57-
} catch (error) {
58-
throw new ConfigurationError(`We got an error trying to parse the LineItems. Error: ${error}`);
59-
}
98+
const lines = this.lineItemsAsObjects
99+
? parseLineItems(this.lineItems)
100+
: this.buildLineItems();
101+
102+
lines.forEach((line) => {
103+
if (line.DetailType !== "SalesItemLineDetail" && line.DetailType !== "GroupLineDetail" && line.DetailType !== "DescriptionOnly") {
104+
throw new ConfigurationError("Line Item DetailType must be `SalesItemLineDetail`, `GroupLineDetail`, or `DescriptionOnly`");
105+
}
106+
});
60107

61108
const response = await this.quickbooks.createInvoice({
62109
$,
63110
data: {
64-
Line: this.lineItems,
111+
Line: lines,
65112
CustomerRef: {
66113
value: this.customerRefValue,
67-
name: this.customerRefName,
68114
},
69115
CurrencyRef: {
70116
value: this.currencyRefValue,
71-
name: this.currencyRefName,
72117
},
73118
},
74-
params: {
75-
minorversion: this.minorVersion,
76-
},
77119
});
78120

79121
if (response) {
80-
$.export("summary", `Successfully created invoice with id ${response.Invoice.Id}`);
122+
$.export("summary", `Successfully created invoice with ID ${response.Invoice.Id}`);
81123
}
82124

83125
return response;

0 commit comments

Comments
 (0)