Skip to main content

Carousell Store Management

This is the installation and configuration guide for Carousell Store Management, the module you downloaded from your ECOSIRE dashboard. Everything on this page describes the carousell_store_management module exactly as it ships today — the facts below were read out of the released build, not from a roadmap.

Technical namecarousell_store_management
Odoo versions17.0, 18.0, 19.0 (Community or Enterprise)
Current shipped version17.0 → 17.0.1.2.2, 18.0 → 18.0.1.2.2, 19.0 → 19.0.1.2.2
Price$499 USD — one-time, per Odoo version, on 17.0, 18.0 and 19.0
Odoo module licenceOPL-1
CategoryConnector
Each Odoo major version is a separate product

The 17.0, 18.0 and 19.0 builds are sold and downloaded separately, and your dashboard offers the file matching the version you bought. If you later upgrade Odoo to a new major version, that version's module is a new purchase. Buy the version you actually run.

The module installs and runs standalone — there is no licence key, no activation step and no separate licence module to install. Licensing is contractual (the OPL-1 licence under which the module is sold). Extract the ZIP, install, configure the connection, and you are running.

Read this before you buy: Carousell API access is partner-gated

Carousell publishes no public seller API — there is no developer portal, no API reference and no self-service sign-up. API access is granted to approved partners by Carousell's Business team.

The module is built for that integration and refuses rather than guesses. Concretely: every capability call is refused until Carousell grants your account API access, and the refusal names the capability, the reason and the next step. The module never calls an address Carousell has not published — which is why a listing, order, inventory, customer, return or payout import will tell you plainly that it is not available on your connection instead of returning an empty list or a fabricated success.

What you can use today, without partner access: the connection record and Test Connection (a connectivity probe against the API base URL — it reports the honest verdict, not a capability test), the local Carousell records and their Odoo mappings, the Operations Center and sync dashboard, the audit trail in Carousell → Operations → Logs, and the four public webhook receivers, which queue an import when Carousell pushes an event. Ask your Carousell account manager to enable API access for your seller account, then contact info@ecosire.com to have the connection turned on.

What this means in practice​

Without Carousell partner API accessWith it
Every capability import refuses, on screen, with the reasonThe same imports run against your seller account
Test Connection still reports the honest reachability verdictUnchanged
Webhook receivers accept and queue deliveriesUnchanged
Local records, mappings, dashboard, logs and Operations Center all workUnchanged

The refusal text is part of the shipped contract, not a bug: it is what stops the module from inventing an endpoint Carousell has never published.

Requirements​

RequirementDetail
Odoo17.0, 18.0 or 19.0, Community or Enterprise. Self-hosted or Odoo.sh — Odoo Online (SaaS) cannot install third-party modules
Odoo appsbase, sale_management, stock, account, delivery, mail, web, portal, product, contacts, digest — Odoo installs any that are missing automatically
Python packagesrequests
Platform accountA Carousell account with API access (OAuth2 client credentials — see Configuration)

Install the Python packages into the same interpreter that runs Odoo:

sudo -u odoo pip install requests

Installation​

1. Download the ZIP for your Odoo version​

Sign in at ecosire.com and open your dashboard downloads. You will be offered the file matching your Odoo version.

2. Extract into your addons path​

unzip carousell_store_management_v19_*.zip -d /opt/odoo/addons/
ls /opt/odoo/addons/carousell_store_management/__manifest__.py # sanity check

The module must end up as a single top-level carousell_store_management/ directory with __manifest__.py directly inside it. If your ls check fails, the folder landed one level too deep or too shallow — move it so the path above resolves.

3. Restart Odoo and install​

sudo systemctl restart odoo
  1. Go to Apps and click Update Apps List (developer mode must be on).
  2. Search for Carousell Store Management and click Install.
  3. Odoo pulls in the Odoo apps listed above automatically.

When the install finishes, a Carousell menu appears in the main Odoo app switcher.

What changed in 19.0.1.2.2 (same changes in the 17.0 and 18.0 builds)​

  • Dark mode themes the whole dashboard. Cards, charts, placeholders and banners follow Odoo's dark colour scheme instead of staying light under a dark menu bar.
  • The Order Status chart draws. It used to stay blank behind its legend. Both charts are now built from the loaded figures, and a chart with nothing to show says No orders in this period or No sales in this period.
  • Exact Sales Trend axis. The revenue axis labels its gridlines exactly (1.5K, 2.5K) instead of rounding two lines to the same "2K".
  • Clear loading, empty and error states. The first load shows placeholders instead of zeros and Not Configured. A connected store with nothing synced for the period says so and points to Sync Now. A company with no Carousell store sees one No Carousell store connected yet panel with Connect a Carousell store and Setup guide, and Sync Now stays hidden until a store exists. A failed load shows the error at the top of the page with Try again and a link to the sync logs.
  • Phone layout. The store name in the dashboard header stays on one line and is shortened with an ellipsis instead of running off the screen.
  • Lists fit a phone. On Queue Jobs the error text and Last Updated, and on Logs the job and message text, are optional columns: hidden by default, shown from the column picker at the right of the list header, and always visible on the record itself. The Products list uses short column titles (Listing ID, Store) and hides the variant ID, last sync and active columns by default; on 17.0 the Customers list does the same (Buyer ID, Contact, Store).
  • Keyboard and contrast. The revenue, orders, customers and products cards open with Enter or Space, and status text meets WCAG AA contrast.

What changed in 19.0.1.2.1 and 19.0.1.2.0 (same changes in the 17.0 and 18.0 builds)​

  • The "Listing Created" webhook handler no longer fails on every event (1.2.1). The dispatcher now resolves the Odoo product the way the importer does — SKU, then barcode, then name — and creates it when the listing is new, so a pushed listing appears in Carousell → Products instead of only moving the error counter.
  • The carrier-visibility repair reaches databases already on 1.1.2 (1.2.1). The repair had been labelled with the older version, so Odoo skipped it on exactly the databases it was written for.
  • The 18.0 and 17.0 builds carry the same test suite as 19.0 (1.2.1) — the Operations Center, every queue handler, the capability refusals, the promise audit and the manager guard now run on all three series.
  • Clearer message when a capability is unavailable (1.2.0). The message now says what is unavailable, why, and what to do next, instead of a generic error.
  • "Created On" and "Last Updated" are filled in properly on Logs and Queue Jobs (1.2.0). Both columns are stamped by Odoo itself on create and on every change; nothing changes on screen.

What changed in 19.0.1.1.0​

  • Standalone install. The module needs nothing installed alongside it and nothing to enable before your first sync. Existing installs update to this version with no action on your side.
  • Buyer details still enrich automatically. Imported customers keep getting cleaned names, resolved country, and state/region (including deriving the state from the postcode) filled in on their res.partner record — the module now carries those helpers itself, and they behave exactly as before.
  • A bad record no longer aborts the whole sync (shipped in 19.0.1.0.13). Every import and sync loop processes each record in its own transaction. If one record is malformed or rejected mid-run, that single record rolls back alone, is written to the module's log with the platform's error text, and the rest of the run completes and commits. Before this change a single bad record could silently discard every good record imported earlier in the same run.

Configuration​

Connect to Carousell​

Create a connection record on the carousell.instance model. The fields the module defines for the connection are:

FieldTechnical nameTypeRequired
Instance NamenameCharYes
Client IDclient_idCharYes
Client Secretclient_secretCharYes
Companycompany_idMany2oneYes
Access Tokenaccess_tokenCharNo
User IDuser_id_extCharNo

The fields marked Yes are enforced by the model — Odoo will not let you save the record without them. The technical name is the reliable identifier if your screen wording differs. The Client ID and Client Secret are the OAuth2 client credentials for your Carousell app; the access token is obtained automatically via the client-credentials flow, so you normally leave that field alone. The User ID, if you fill it, filters listings to your Carousell seller account.

The same record carries 3 behaviour checkboxes — auto_confirm_order, auto_create_invoice, auto_validate_invoice. They gate what the module is allowed to do automatically once it is connected. Leave anything you are not ready for switched off, and turn them on one at a time.

The instance also carries the defaults imported documents land on: default warehouse, pricelist, salesperson, payout journal, and the discount and shipping products used on imported orders; the risk thresholds used by risk detection; and the monthly marketing cost / operating expenses used by the analytics.

Use the Test Connection button on the instance form after saving — it exercises the credentials against the API and reports the platform's own response.

The module's own source contacts api.carousell.com over HTTPS. Your firewall must allow outbound HTTPS to it.

Scheduled actions​

The module installs 12 scheduled actions (Settings → Technical → Scheduled Actions):

Scheduled actionRuns everyEnabled on install
Carousell: Sync Products30 minutesYes
Carousell: Sync Orders15 minutesYes
Carousell: Sync Customers60 minutesYes
Carousell: Sync Inventory10 minutesYes
Carousell: Process Queue Jobs5 minutesYes
Carousell: Import Payout Reports6 hoursYes
Carousell: Auto Risk Detection30 minutesYes
Carousell: Generate Analytics4 hoursYes
Carousell: Webhook Health Check60 minutesYes
Carousell: Cleanup Old Logs24 hoursYes
Carousell: Process Workflows10 minutesYes
Carousell: Daily Summary Report1 dayYes

Intervals above are the shipped defaults. Adjust them to your volume — but be aware that the platform, not Odoo, sets the API rate limits, and shortening a sync interval is the usual cause of throttling errors in the logs. Refunds and payouts are imported on demand through the operations wizard, or pushed to the webhook endpoints below — there is no separate refund cron.

These jobs are scheduled, not necessarily successful

Every job above is installed and scheduled. Whether its import can fetch anything depends on your Carousell account having partner API access — without it the job runs, refuses the capability with a logged reason, and completes without importing. See the access note at the top of this page. The local, non-platform jobs (queue processing, risk detection, analytics, webhook health, log cleanup, workflows, daily summary) work regardless.

Webhooks​

Webhooks let Carousell push events to Odoo the moment they happen, instead of waiting for the next sync interval. The module has two halves.

Registering webhooks (outbound)​

Carousell → Configuration → Webhooks holds one record per event you follow — listing created / updated / deleted, order created / updated / fulfilled / cancelled, inventory updated, return created / updated, wallet transaction. Each record carries retry, timeout and batch-size settings, and a Test action that sends a signed sample payload to the delivery URL so you can verify the wiring. Creating the record prepares the configuration inside Odoo; the delivery URL itself is registered manually in your Carousell seller portal.

The receiver endpoints (inbound)​

The module listens on four public HTTP endpoints. Each accepts POST only and requires no Odoo session:

EndpointQueues an import of
/carousell/webhook/producta product / listing
/carousell/webhook/orderan order
/carousell/webhook/customera customer
/carousell/webhook/refunda refund

How an incoming delivery is handled:

  1. Instance resolution — the X-Carousell-Shop-Domain request header is matched against your instances to find the connection the event belongs to.
  2. Signature check — the X-Carousell-Hmac-SHA256 header must carry the base64-encoded HMAC-SHA256 of the raw request body. A delivery without a valid signature is rejected.
  3. Queuing — an accepted delivery creates a pending queue job (Carousell → Operations → Queue Jobs) plus a log record, and the Carousell: Process Queue Jobs scheduled action imports it within its 5-minute interval. The endpoint answers {"status": "ok"} immediately; a rejected delivery answers {"status": "error"} with the reason.

Because the endpoints are public, they only ever receive data — a delivery can queue an import; it cannot read anything out of your Odoo.

Using the module​

The module's menu is laid out as:

  • Carousell → Dashboard
  • Carousell → Orders
  • Carousell → Refunds
  • Carousell → Products
  • Carousell → Customers
  • Carousell → Payouts
  • Carousell → Analytics
  • Carousell → Operations — Run Operations, Queue Jobs, Logs
  • Carousell → Configuration — Instances, Locations, Payment Gateways, Scheduled Actions, Webhooks

A normal first run is:

  1. Save the connection record and click Test Connection — confirm it reports success before importing anything.
  2. Review the remaining settings on the instance and its Configuration records (locations, payment gateways, warehouse / pricelist / journal defaults) so imported data lands on the right Odoo records.
  3. Run a small import first — restrict it by date or by a handful of products — and check the results before letting the scheduled actions take over. Carousell → Operations → Run Operations opens the manual sync wizard for this.
  4. Watch the log records during the first full sync. Failures are recorded there rather than raised at the user — a record the platform rejects is logged and skipped, and the run continues.

Troubleshooting​

Symptom / error codeCause and fix
The requests library is requiredrequests is missing from Odoo's Python environment. Install it into the interpreter that runs Odoo.
The connection will not validateRe-check every required field in the table above. Most failures are a mistyped secret, or credentials created for a sandbox while the module points at production (or vice-versa).
Nothing syncs even though the connection is fineFirst check the log record for the run: if the capability is refused, your Carousell account does not have partner API access yet — see the access note at the top of this page. If it was not refused, then the scheduled actions are disabled at the Odoo level, or Odoo's cron worker is not running. Check Settings → Technical → Scheduled Actions and that --max-cron-threads is greater than zero.
Sync starts then stops part-wayRead the module's log records for that run. Rate limiting and rejected field values are the two common causes; both are logged with the platform's own error text.
One record fails but the rest importedThat is the containment behaviour working as designed since 19.0.1.0.13 — the rejected record is rolled back alone and logged, and the rest of the run commits. Fix or skip the record based on the logged platform error.
Records import but map to the wrong Odoo valuesFix the settings on the instance and its Configuration records, then re-run the import.
Duplicated products or customersRun the initial import once. If a first attempt half-finished, check the existing records before re-running rather than importing on top.
Webhook deliveries answer {"status": "error"}The delivery is rejected when the X-Carousell-Shop-Domain header matches no configured instance, or the X-Carousell-Hmac-SHA256 signature header is missing or does not verify. Confirm the sender sets both headers and that the shop domain matches your instance record.
A webhook arrived but nothing importedInbound deliveries are queued, not imported inline. Check Carousell → Operations → Queue Jobs for a pending job and let the Process Queue Jobs scheduled action run — or trigger it from Configuration → Scheduled Actions.

Version history​

Odoo versionVersion you download today
17.017.0.1.2.2
18.018.0.1.2.2
19.019.0.1.2.2

ECOSIRE module versions are <odoo major>.<module major>.<minor>.<patch>, so 19.0.1.2.2 is the Odoo 19 build of module version 1.2.2. Your installed version is shown in Apps.

Support​