Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion .github/workflows/plugin-check.yml
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ jobs:
- name: Install pnpm
uses: pnpm/action-setup@v4
with:
version: 9
run_install: false

- name: Get pnpm store directory
Expand Down Expand Up @@ -66,7 +67,7 @@ jobs:

- name: Build plugin
run: |
pnpm production
pnpm build
bash .github/copy-assets

- name: WordPress Plugin Check
Expand Down
39 changes: 30 additions & 9 deletions backend/Actions/ActiveCampaign/RecordApiHelper.php
Original file line number Diff line number Diff line change
Expand Up @@ -132,20 +132,41 @@ private function handleRelatedActions($contactId, $listId, $tags, $integrationDe
];
$result['lists'] = $this->storeOrModifyRecord('contactLists', wp_json_encode($data));
}

if (!empty($tags)) {
// Remove existing tags if tag update is enabled
if ($integrationDetails->actions->tagUpdate) {
$result['tags_removed'] = HttpHelper::delete("{$this->_apiEndpoint}/contactTags/{$contactId}", null, $this->_defaultHeader);
$contactTagsResponse = HttpHelper::get("{$this->_apiEndpoint}/contacts/{$contactId}/contactTags", null, $this->_defaultHeader);
$contactTags = $contactTagsResponse->contactTags ?? [];

if (!empty($contactTags)) {
foreach ($contactTags as $contactTag) {
HttpHelper::delete("{$this->_apiEndpoint}/contactTags/{$contactTag->id}", null, $this->_defaultHeader);
$result['tags_removed'][] = HttpHelper::$responseCode === 200
? __('Tag removed successfully', 'bit-integrations')
: __('Failed to remove tag', 'bit-integrations');
}
Comment on lines +143 to +148

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

high

This loop makes an individual API request for each tag to be deleted. If a contact has a large number of tags, this can lead to poor performance and potentially hit API rate limits. While the ActiveCampaign API may not offer a bulk delete endpoint for contact tags, it's worth double-checking if a more efficient method is available.

Additionally, the code relies on a static property HttpHelper::$responseCode to check the status of the delete operation. This is not a robust pattern as static properties can introduce side effects. It would be better to use the return value from HttpHelper::delete() to determine the outcome of the request.

} else {
$result['tags_removed'] = __('No tags to remove', 'bit-integrations');
}
}

$result['tags_added'] = [];
foreach ($tags as $tag) {
$data['contactTag'] = (object) [
'contact' => $contactId,
'tag' => $tag
];
$result['tags_added'][] = $this->storeOrModifyRecord('contactTags', wp_json_encode($data));
}
// Add new tags
$result['tags_added'] = array_map(
function ($tag) use ($contactId) {
$data = [
'contactTag' => (object) [
'contact' => $contactId,
'tag' => $tag
]
];

return $this->storeOrModifyRecord('contactTags', wp_json_encode($data));
},
$tags
);
}

if (!empty($integrationDetails->selectedAccount)) {
$data['accountContact'] = [
'account' => $integrationDetails->selectedAccount,
Expand Down
2 changes: 1 addition & 1 deletion backend/Config.php
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ class Config

public const VAR_PREFIX = 'bit_integrations_';

public const VERSION = '2.7.12';
public const VERSION = '2.8.0';

public const DB_VERSION = '1.1';

Expand Down
9 changes: 7 additions & 2 deletions backend/Triggers/WC/WCHelper.php
Original file line number Diff line number Diff line change
Expand Up @@ -251,8 +251,13 @@ public static function accessOrderData($order)
}

foreach ($order->get_items() as $item) {
if (empty($item)) {
continue;
}

$productId = $item->get_product_id();
$product = $item->get_product();

$itemData = [
'product_id' => $productId,
'variation_id' => $item->get_variation_id() ?? '',
Expand All @@ -263,8 +268,8 @@ public static function accessOrderData($order)
'subtotal_tax' => $item->get_subtotal_tax() ?? '',
'tax_class' => $item->get_tax_class() ?? '',
'tax_status' => $item->get_tax_status() ?? '',
'product_sku' => $product->get_sku() ?? '',
'product_unit_price' => $product->get_price() ?? '',
'product_sku' => $product && $product->get_sku() ? $product->get_sku() : '',
'product_unit_price' => $product && $product->get_price() ? $product->get_price() : '',
Comment on lines +271 to +272

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

The added checks for the $product object are great for preventing fatal errors. However, the ternary expression can be simplified for better readability. Since get_sku() and get_price() return strings, you can make this more concise.

                'product_sku'        => $product ? $product->get_sku() : '',
                'product_unit_price' => $product ? $product->get_price() : '',

Comment on lines +271 to +272
];

$acfFieldGroups = Helper::acfGetFieldGroups(['product']);
Expand Down
4 changes: 2 additions & 2 deletions bitwpfi.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
* Plugin Name: Bit Integrations
* Plugin URI: https://bitapps.pro/bit-integrations
* Description: Bit Integrations is a platform that integrates with over 300+ different platforms to help with various tasks on your WordPress site, like WooCommerce, Form builder, Page builder, LMS, Sales funnels, Bookings, CRM, Webhooks, Email marketing, Social media and Spreadsheets, etc
* Version: 2.7.12
* Version: 2.8.0
* Author: Automation & Integration Plugin - Bit Apps
* Author URI: https://bitapps.pro
* Text Domain: bit-integrations
Expand Down Expand Up @@ -33,7 +33,7 @@
*
* @deprecated 2.7.8 Use Config::VERSION instead.
*/
define('BTCBI_VERSION', '2.7.12');
define('BTCBI_VERSION', '2.8.0');
/**
* deprecated since version 2.7.8.
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ import PayLoadFieldMap from './PayLoadFieldMap'
function Body({ webHooks, setWebHooks, isInfo, setTab }) {
const formFields = useRecoilValue($formFields)
const formattedFormFields = useMemo(
() => formFields.map(field => ({ key: field.name, value: `\${${field.name}}` })),
() => formFields?.map(field => ({ key: field.name, value: `\${${field.name}}` })),

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

high

Using optional chaining (?.) is a good step to prevent errors when formFields is null or undefined. However, the default value for the $formFields atom is an empty object ({}), which is not an array and does not have a .map method. This will still cause a runtime error.

To make this more robust, you should check if formFields is an array before calling .map.

Suggested change
() => formFields?.map(field => ({ key: field.name, value: `\${${field.name}}` })),
() => (Array.isArray(formFields) ? formFields.map(field => ({ key: field.name, value: `\${${field.name}}` })) : []),

[formFields]
)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,11 @@ import { __ } from '../../../../Utils/i18nwrap'
export const getFluentFluentBookingFields = (setFlowData, value, edit, setFormFields) => {
const loadFields = bitsFetch({ id: value }, 'fluentbooking/get/fields', null, 'POST').then(result => {
if (result && result.success) {
if (edit) {
setFormFields(result.data)
} else {
setFormFields(result.data)

if (!edit) {
setFlowData(result.data, 'fields')
}
}

return __('Fetched fields successfully', 'bit-integrations')
}
Expand Down
70 changes: 37 additions & 33 deletions frontend/src/pages/ChangelogToggle.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -30,77 +30,81 @@ const changeLog = [
label: __('New Actions', 'bit-integrations'),
headClass: 'new-integration',
itemClass: 'integration-list',
items: []
items: [
{
label: 'User Registration & Membership',
desc: '1 new events added',
isPro: true
}, {
label: 'NotificationX',
desc: '7 new events added',
isPro: true
}
]
},
{
label: __('New Triggers', 'bit-integrations'),
headClass: 'new-trigger',
itemClass: 'integration-list',
items: []
items: [
{
label: 'User Registration & Membership',
desc: '2 new events added',
isPro: true
}, {
label: 'NotificationX',
desc: '2 new events added',
isPro: true
}
]
},
{
label: __('New Features', 'bit-integrations'),
headClass: 'new-feature',
itemClass: 'feature-list',
items: [
{
label: 'ActiveCampaign',
desc: 'Tags update feature added.',
isPro: false
label: 'Forminator Quiz & Poll',
desc: 'Included lead data in quiz trigger payloads.',
isPro: true
}
]
},
{
label: __('Improvements', 'bit-integrations'),
headClass: 'new-improvement',
itemClass: 'feature-list',
items: [
{
label: 'ActiveCampaign',
desc: 'Refactored update contact handling.',
isPro: false
},
{
label: 'Custom Function',
desc: 'Improved validator logic.',
isPro: false
},
{
label: 'get-access-token',
desc: 'Removed unnecessary sanitation on get-access-token routes for smoother OAuth flow.',
isPro: false
}
]
items: []
},
{
label: __('Bug Fixes', 'bit-integrations'),
headClass: 'fixes',
itemClass: 'fixes-list',
items: [
{
label: 'SendFox',
desc: 'Fixed blank page issue and fieldmap disappearance issue.',
label: 'GoHighLevel',
desc: 'Fixed opportunity creation by sending the selected pipeline ID correctly.',
isPro: false
},
{
label: 'WooCommerce',
desc: 'Fixed billing and shipping address overwrite issue.',
label: 'ActiveCampaign',
desc: 'Fixed tag update handling so existing tags are removed correctly before new tags are applied.',
isPro: false
},
{
label: 'Salesforce',
desc: 'Fixed lead response type issue.',
label: 'FluentBooking',
desc: 'Fixed fetched fields not being set consistently during trigger configuration.',
isPro: false
},
{
label: 'Google Products',
desc: 'Fixed authentication issue.',
label: 'Webhook',
desc: 'Fixed payload field mapping when form fields are unavailable during setup.',
isPro: false
},
{
label: 'Brekadance',
desc: 'Fixed trigger listening data issue.',
isPro: true
label: 'WooCommerce',
desc: 'Fixed product data access issues for order items without product objects.',
isPro: false
}
]
},
Expand Down
Binary file modified frontend/src/resource/img/integ/voxel.webp
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
16 changes: 14 additions & 2 deletions languages/bit-integrations.pot
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,14 @@
# This file is distributed under the GPLv2 or later.
msgid ""
msgstr ""
"Project-Id-Version: Bit Integrations 2.7.11\n"
"Project-Id-Version: Bit Integrations 2.7.12\n"
"Report-Msgid-Bugs-To: https://wordpress.org/support/plugin/bit-integrations\n"
"Last-Translator: developer@bitcode.pro\n"
"Language-Team: support@bitcode.pro\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"POT-Creation-Date: 2026-03-07T09:14:31+00:00\n"
"POT-Creation-Date: 2026-03-13T05:59:46+00:00\n"
Comment on lines +5 to +12
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"X-Generator: WP-CLI 2.11.0\n"
"X-Domain: bit-integrations\n"
Expand Down Expand Up @@ -705,6 +705,18 @@ msgstr ""
msgid "Email already exist"
msgstr ""

#: backend/Actions/ActiveCampaign/RecordApiHelper.php:146
msgid "Tag removed successfully"
msgstr ""

#: backend/Actions/ActiveCampaign/RecordApiHelper.php:147
msgid "Failed to remove tag"
msgstr ""

#: backend/Actions/ActiveCampaign/RecordApiHelper.php:150
msgid "No tags to remove"
msgstr ""

#: backend/Actions/Affiliate/RecordApiHelper.php:154
msgid "User are not affiliate"
msgstr ""
Expand Down
Loading
Loading