84 Commits
Author SHA1 Message Date
Tautvydas Derzinskas f7c6e058f2 ci(extension): check Edge certification notes fit Edge's limit 2026-10-20 09:23:27 +02:00
Tautvydas Derzinskas f240dce392 fix(extension): list sync storage and Snapmaker renewal in Edge notes 2026-10-20 09:18:43 +02:00
Tautvydas Derzinskas 900731fbd9 fix(extension): narrow the data claim in Edge certification notes 2026-10-20 09:09:15 +02:00
Tautvydas Derzinskas d33802d8c0 fix: prevent AMO rate limit errors in extension release
Serialize publish-firefox and publish-latest jobs with a 90-second delay
to prevent hitting AMO's rate limit when running in parallel. Ensure
publish-latest still runs even if publish-firefox fails, while
maintaining the job dependency.

Also simplify extension certification notes.
2026-10-20 08:56:24 +02:00
github-actions[bot] c7ebbeebba chore(extension): release 1.7.0
# [thingport-grab-v1.7.0](https://github.com/TautvydasDerzinskas/Thingport/compare/thingport-grab-v1.6.0...thingport-grab-v1.7.0) (2026-10-20)

### Bug Fixes

* add validation and improve error handling in sync operations ([7c3c7ec](https://github.com/TautvydasDerzinskas/Thingport/commit/7c3c7ec90298672150219ea18c44ac37bc40280c))
* correct category updates and improve NexPrint error handling ([1cf2903](https://github.com/TautvydasDerzinskas/Thingport/commit/1cf2903b8efd9e13f71b50e4e768f7930c1382eb))
* detect Cults3D clearance cookie in Cloudflare partitions ([2f66ed6](https://github.com/TautvydasDerzinskas/Thingport/commit/2f66ed682b1bc61b0a6c456db23aedbc15193eb1))
* handle malformed tokens, add refresh concurrency control, and improve list URL validation ([44f4bf2](https://github.com/TautvydasDerzinskas/Thingport/commit/44f4bf26354675ce41ee0c7e2684d3fe9384e70f))
* Makerworld profile thumbnails being all the same ([c6c8161](https://github.com/TautvydasDerzinskas/Thingport/commit/c6c8161a74dceca83d0827fec00735763ce76428))
* tell print profiles apart by name and picture on every provider ([f34a488](https://github.com/TautvydasDerzinskas/Thingport/commit/f34a488fb21b69b50e8170105f5933f70cf46f01))

### Features

* add Cults3D provider ([930b9b4](https://github.com/TautvydasDerzinskas/Thingport/commit/930b9b48dba5c2375d4fccf2e59ced2965e87711))
* add MyMiniFactory as a provider ([a7a9190](https://github.com/TautvydasDerzinskas/Thingport/commit/a7a91902a0f43d47741e8cb52c1ec294f143fadb))
* add Thangs provider ([2591714](https://github.com/TautvydasDerzinskas/Thingport/commit/2591714c0cd44b086c0cb3c94d11e99c8262fe81))
* enable Creality Cloud provider ([772b1ac](https://github.com/TautvydasDerzinskas/Thingport/commit/772b1acfef609796015b51db186012e717124bc5))
* enable NextPrint provider ([4037151](https://github.com/TautvydasDerzinskas/Thingport/commit/4037151e4aaa6a744469b52ef60f999b343e085a))
* **providers:** enable MakerOnline provider ([5bf3457](https://github.com/TautvydasDerzinskas/Thingport/commit/5bf3457e8c5a5448c97f12fb0ac9101137884dca))
* **providers:** enable Snapmaker Space provider ([ac5bf25](https://github.com/TautvydasDerzinskas/Thingport/commit/ac5bf253c7c3a09abd0ce90e8c24539004f0f879))
2026-10-20 06:36:59 +00:00
Tautvydas Derzinskas 233c794065 docs: add a setup page per provider and a comparison of all ten
Each provider gets its own page under docs/providers/ with a short description,
what it needs (sign-in, Thingport Grab, FlareSolverr) and its setup steps, with
the provider's icon as an accent. PROVIDER_SETUP.md becomes the overview, with a
dependency and feature table. MakerWorld, Printables and Thingiverse come first
everywhere.
2026-10-20 05:57:23 +02:00
Tautvydas Derzinskas 2f66ed682b fix: detect Cults3D clearance cookie in Cloudflare partitions 2026-10-20 05:17:12 +02:00
Tautvydas Derzinskas 930b9b48db feat: add Cults3D provider
Imports Cults3D models, anyone's likes and the user's own printlists, and
syncs them. Metadata comes from Cults3D's GraphQL API with each user's own
nickname and API key. The API never hands out files, and the site's pages are
behind a Cloudflare check only a browser passes, so Thingport Grab sends the
browser's _session_id and cf_clearance cookies with its User-Agent; with
them the server orders a free model for nothing, as its Download button
does, and follows the download page to the signed file link (CloudFront, or
Cults3D's Scaleway bucket for older models). Paid models download once
bought. A Cloudflare block defers a sync until the next visit with Grab.
2026-10-20 05:08:08 +02:00
Tautvydas Derzinskas a2feeccdcd refactor(thangsSession): merge error handling in cookieValue, return undefined on error
Previously, decode errors returned empty string which could clear a
stored session. Now both error paths return undefined to skip sync,
matching snapmakerSession.ts behavior.
2026-10-20 00:27:58 +02:00
Tautvydas Derzinskas 7c3c7ec902 fix: add validation and improve error handling in sync operations
- Hide API keys from error messages by stripping query strings
- Validate that category responses contain entries before using them
- Distinguish between unreadable and malformed cookie values with proper types
2026-10-20 00:17:12 +02:00
Tautvydas Derzinskas 2591714c0c feat: add Thangs provider
Imports Thangs models, likes and collections, and syncs them. Metadata is
public; files need the user's own sign-in, which Thingport Grab sends and
Thingport renews from the refresh token. Paid models download once owned;
print-only ones are refused before any download. Free accounts' daily
download limit stops a batch and defers the rest of a sync to its next check.
2026-10-19 23:36:07 +02:00
Tautvydas Derzinskas f34a488fb2 fix: tell print profiles apart by name and picture on every provider
Profile files often come named alike, so the files on a model read the
same. A profile whose file clashes with another profile's is now named
after its profile, or by its title alone when that already holds the
file's name; profiles with the same title keep the site's name.

Each profile's own picture now becomes its file's thumbnail on Snapmaker
Space, MakerOnline, Creality Cloud and NexPrint too, not just MakerWorld.

Earlier profiles are renamed before the new file is placed, and a preview
render that loses its file to a rename retries from where it went.
2026-10-19 20:34:24 +02:00
Tautvydas Derzinskas c6c8161a74 fix: Makerworld profile thumbnails being all the same 2026-10-19 20:06:07 +02:00
Tautvydas Derzinskas 1cf2903b8e fix: correct category updates and improve NexPrint error handling 2026-10-19 18:39:24 +02:00
Tautvydas Derzinskas 4037151e4a feat: enable NextPrint provider 2026-10-19 18:18:26 +02:00
Tautvydas Derzinskas 42be6fb988 refactor: validate Creality Cloud account and improve session handling 2026-10-19 14:34:50 +02:00
Tautvydas Derzinskas 772b1acfef feat: enable Creality Cloud provider 2026-10-19 14:13:45 +02:00
Tautvydas Derzinskas fe4794da69 refactor: improve import handling and sync reliability 2026-10-19 08:46:12 +02:00
Tautvydas Derzinskas 5bf3457e8c feat(providers): enable MakerOnline provider 2026-10-19 07:41:05 +02:00
Tautvydas Derzinskas 44f4bf2635 fix: handle malformed tokens, add refresh concurrency control, and improve list URL validation
- Wrap decodeURIComponent in try-catch to handle malformed percent-encoding
- Add inFlight promise to prevent concurrent callers from reusing single-use refresh tokens
- Require list parameter to be "likes" or "bookmarks" for Snapmaker list URLs
- Update documentation to clarify Snapmaker sign-in renewal and token transmission
2026-10-19 01:20:18 +02:00
Tautvydas Derzinskas ac5bf253c7 feat(providers): enable Snapmaker Space provider 2026-10-19 00:57:12 +02:00
Tautvydas Derzinskas be9d0f0cbe refactor: address pr comments 2026-10-18 21:45:22 +02:00
Tautvydas Derzinskas 24bb8d430a refactor: update extension popup and address pr comments 2026-10-18 21:21:42 +02:00
Tautvydas Derzinskas a7a91902a0 feat: add MyMiniFactory as a provider
Import, collection import and synced collections from MyMiniFactory, alongside MakerWorld,
Printables and Thingiverse.

- Backend: API v2 client with an instance-wide API key for metadata, collections and
  authors; files from MyMiniFactory's own download links (free models need no login).
  Paid models, and free ones whose files are archives, download as the user from their
  MyMiniFactory library through their session (PHPSESSID), fetching the model files
  MyMiniFactory unpacked from each archive. Paid models are left out of collection
  listings and syncs.
- One migration: MyMiniFactory category ids, username and session columns, plus a data
  migration giving existing users' starter categories the new category ids. Category
  matching now prefers the most specific site category.
- Frontend: provider everywhere the others appear (badges, Configuration and
  Administration providers, sync Browse tab, user menu, link detection, System Health,
  category ids), shared instance-key form for Thingiverse and MyMiniFactory, en and lt.
- Thingport Grab: new provider sites are allowed once from the popup (optional
  all-sites access, content script registered at runtime), so adding one never makes
  the browser disable the extension; captures the signed-in MyMiniFactory username and
  session; paid-model notice.
- Docs, website, store assets and screenshots updated.
2026-10-18 18:19:43 +02:00
Tautvydas Derzinskas c775590655 ci: publish extension-latest with store releases, not every merge
The per-merge workflow now only runs checks. The store release moves
extension-latest to the released build, with an unlisted-signed .xpi.
2026-10-18 08:15:59 +02:00
github-actions[bot] 0c26f41107 chore(extension): release 1.6.0
# [thingport-grab-v1.6.0](https://github.com/TautvydasDerzinskas/Thingport/compare/thingport-grab-v1.5.0...thingport-grab-v1.6.0) (2026-10-17)

### Bug Fixes

* **import:** stop flagging models that mention robots as a MakerWorld CAPTCHA, and let a manual retry try again ([#18](https://github.com/TautvydasDerzinskas/Thingport/issues/18)) ([d70dcfe](https://github.com/TautvydasDerzinskas/Thingport/commit/d70dcfeac2c788686728598c6d3c61b9f4cce369))
* skip a stale MakerWorld defaultInstanceId when picking the print profile ([#15](https://github.com/TautvydasDerzinskas/Thingport/issues/15)) ([d5ae809](https://github.com/TautvydasDerzinskas/Thingport/commit/d5ae80951cf69a9a4db118eee4f68d332f0af17a)), closes [#14](https://github.com/TautvydasDerzinskas/Thingport/issues/14)

### Features

* administration settings remake + OIDC support ([#49](https://github.com/TautvydasDerzinskas/Thingport/issues/49)) ([9a22386](https://github.com/TautvydasDerzinskas/Thingport/commit/9a2238691d8b079adf7bfb4becebc9cf01cb6cad))
* system notifications updates, Thingport grab in System health check, node 24+ ([#52](https://github.com/TautvydasDerzinskas/Thingport/issues/52)) ([358dfc1](https://github.com/TautvydasDerzinskas/Thingport/commit/358dfc1a03a178115642d41423f40586cd879b90))
2026-10-17 17:30:59 +02:00
Tautvydas Derzinskas 358dfc1a03 feat: system notifications updates, Thingport grab in System health check, node 24+ (#52)
* feat: update system notifications

* feat: add Thingport grab to system health check

* ci: upgrade to Node.js 24 and centralize version management
2026-10-17 10:44:13 +02:00
Tautvydas Derzinskas 9a2238691d feat: administration settings remake + OIDC support (#49)
* feat: expand storage usage reporting with disk breakdown

* feat: add providers admin view

* feat(storage): add background reorganization and admin browser

Adds background-driven storage reorganization for moving model files
when the storage template changes, with an admin interface to preview
changes, check impact, monitor progress, and browse the storage tree
built from plate records rather than filesystem walks.

* feat: new auth admin settings page + OIDC support

* test: fix failing test
2026-10-17 05:07:24 +02:00
Rui Valim d70dcfeac2 fix(import): stop flagging models that mention robots as a MakerWorld CAPTCHA, and let a manual retry try again (#18)
* fix(import): stop flagging models that mention robots as a MakerWorld CAPTCHA, and let a manual retry try again

isCaptchaChallenge looked for "captcha" or "robot" in every top-level string of a reply,
design titles and summaries included, so a model named "Robot ..." failed as a CAPTCHA on
every retry and started the 2h cooloff for every other import. Only a captcha key or the
reply's own error, message or msg text counts now.

The cooloff also failed a retry straight away after the user solved the puzzle in the
browser, which is what the error message tells them to do. Starting or retrying a queue job
by hand, a bulk start or retry, and POST /import/jobs/:id/retry now lift it. Automatic
collection syncs still respect it.

* feat(extension): offer "Add to the queue" when MakerWorld blocks an import

A CAPTCHA or the daily download limit won't clear by clicking Import again, so the error
panel lets an admin park the link in the queue with the same collection and profile scope.

* fix(import): let a queue job cut off by a restart be started or retried

A restart marks a running job ERROR with its links still PENDING or RUNNING. The queue page
only offered Start for PAUSED jobs and Retry for jobs with FAILED links, and the API agreed,
so such a job could never run again. The same held for a job whose runner crashed.

Start now takes an ERROR job with links waiting, and a retry reruns links an interrupted
run never reached even when none of them failed.
2026-10-14 10:18:48 +02:00
Paul TrainaandClaude Opus 5.5 d5ae80951c fix: skip a stale MakerWorld defaultInstanceId when picking the print profile (#15)
MakerWorld can leave a design's defaultInstanceId pointing at a print profile that no longer
exists. pickMakerworldInstanceId (extension) and makerworldInstanceIdFromNextData (backend)
returned it unchecked, so the download-link request went to the dead profile and MakerWorld
answered 403 "The client does not have access rights to the content." Use the default only when
it is still one of the design's instances, otherwise the first, as selectMakerworldProfiles
already does.

Fixes #14


Claude-Session: https://claude.ai/code/session_01KGCb65Zhzwd3daF862ZE6R

Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-13 06:47:04 +02:00
github-actions[bot] 2d433dff17 chore(extension): release 1.5.0
# [thingport-grab-v1.5.0](https://github.com/TautvydasDerzinskas/Thingport/compare/thingport-grab-v1.4.0...thingport-grab-v1.5.0) (2026-10-12)

### Bug Fixes

* **extension:** check a MakerWorld collection against the library in one call ([44c687b](https://github.com/TautvydasDerzinskas/Thingport/commit/44c687b3ae7ba96a7246ece73d79212733cfd449))

### Features

* browse private collections functionality ([b619084](https://github.com/TautvydasDerzinskas/Thingport/commit/b619084be7ed060d02cd6ba473a196e7ba0859de))
* **collections:** add many models to a collection in one call ([acfa844](https://github.com/TautvydasDerzinskas/Thingport/commit/acfa844ebe62ee635941a2a6d499083cf4856d47))
* **collections:** turn sync on from Thingport, picking the provider's collection ([1131700](https://github.com/TautvydasDerzinskas/Thingport/commit/1131700ec5eb53801a85c842143717c66696d8d8))
* **extension:** show when Thingport Grab can't sign in ([623cf25](https://github.com/TautvydasDerzinskas/Thingport/commit/623cf25f2c43d153b6e89952ab572923558aa6b7))
* **extension:** tell Thingport who you're signed in as on Printables and Thingiverse ([d3ed673](https://github.com/TautvydasDerzinskas/Thingport/commit/d3ed67342aae85bc170b95b01b7aba9dfcab15e0))
* **notifications:** reinvent notifications ([1408b09](https://github.com/TautvydasDerzinskas/Thingport/commit/1408b09c5989499b38ee0effd1b7c29661a233a5))
* **sync:** notify on enable, change defaults to daily and designer profiles ([9334438](https://github.com/TautvydasDerzinskas/Thingport/commit/9334438a521a2a5f9a39f6af4d892ac2465c02ce))
2026-10-12 11:42:48 +00:00
Tautvydas Derzinskas b619084be7 feat: browse private collections functionality 2026-10-12 12:54:26 +02:00
Tautvydas Derzinskas d3ed67342a feat(extension): tell Thingport who you're signed in as on Printables and Thingiverse
So the web app's Browse tab can list the user's collections there
without asking for a username. Thingiverse's comes from the page
header's own account link; Printables' from its API's `me`, asked with
the session token the way the site does. Sent only when it changes.
2026-10-12 05:31:19 +02:00
Tautvydas Derzinskas 1131700ec5 feat(collections): turn sync on from Thingport, picking the provider's collection
Every collection's Sync configuration now works before it's synced: a
Browse tab lists the user's own collections on MakerWorld (through
their cookie, private ones included), Printables and Thingiverse (by a
username asked once), and takes any collection's link. Each provider's
collections are drawn in its own colours and manner.

On Printables and Thingiverse the collection's current models are
imported by the sync's first check. MakerWorld rate-limits bulk
imports, so there only models added from now on come in. Settings can
be picked before turning sync on.
2026-10-12 05:31:01 +02:00
Tautvydas Derzinskas 9334438a52 feat(sync): notify on enable, change defaults to daily and designer profiles 2026-10-12 04:08:24 +02:00
Tautvydas Derzinskas acfa844ebe feat(collections): add many models to a collection in one call
Add POST /collection/:id/items. Thingport Grab uses it to file a
MakerWorld collection's already-imported models instead of one request
per model, falling back on older instances.
2026-10-12 03:50:57 +02:00
Tautvydas Derzinskas 623cf25f2c feat(extension): show when Thingport Grab can't sign in
A session token outlives a password change, so a stale saved password
only surfaced days later as failing imports. Check the connection by
signing in (at most every 10 minutes) at browser start, before showing
the in-page icon, and when the popup opens.

When it fails, the icon shows a "not connected" badge whose dialog says
whether the credentials were rejected or the instance didn't answer,
and opens the popup's edit form. The toolbar icon gets a badge too.
Concurrent calls with an expired token now share one sign-in.
2026-10-12 03:50:46 +02:00
Tautvydas Derzinskas 44c687b3ae fix(extension): check a MakerWorld collection against the library in one call
The collection panel sent one /import/status request per model, all at
once. When any failed it counted the model as new, so a collection
already imported could offer to import almost everything again.

Add POST /import/status/batch and use it, falling back to paced
per-model checks on older instances. A failed check now shows an error
instead of guessing.
2026-10-12 03:50:28 +02:00
Tautvydas Derzinskas 1408b09c59 feat(notifications): reinvent notifications 2026-10-11 23:20:21 +02:00
Tautvydas Derzinskas e24e797999 docs: add synced collections guide and showcase 2026-10-09 07:42:42 +02:00
github-actions[bot] d01c4ee592 chore(extension): release 1.4.0
# [thingport-grab-v1.4.0](https://github.com/TautvydasDerzinskas/Thingport/compare/thingport-grab-v1.3.0...thingport-grab-v1.4.0) (2026-10-08)

### Bug Fixes

* **extension:** store imports in shared storage ([84b4f5b](https://github.com/TautvydasDerzinskas/Thingport/commit/84b4f5bd141e2187cbfe980f7cfc9925829fd467))
* **extension:** use template for Edge certification notes ([30be8c4](https://github.com/TautvydasDerzinskas/Thingport/commit/30be8c434901438225f4a3fd15ed63c222ce4173))

### Features

* **collection-sync:** allow syncing collections with provider collections ([ef9152d](https://github.com/TautvydasDerzinskas/Thingport/commit/ef9152df6cd0edee4fff8355434c9e2e09f73731)), closes [#10](https://github.com/TautvydasDerzinskas/Thingport/issues/10)
* handle download limit error gracefully ([fd7c26a](https://github.com/TautvydasDerzinskas/Thingport/commit/fd7c26a760b82142b8be74634f1461e2007d5ab1))
2026-10-08 23:07:11 +00:00
Tautvydas Derzinskas ef9152df6c feat(collection-sync): allow syncing collections with provider collections
Implements #10
2026-10-09 00:34:44 +02:00
Tautvydas Derzinskas 9df01d0ed5 docs: update docs, screenshots & site 2026-10-08 19:20:54 +02:00
Tautvydas Derzinskas 30be8c4349 fix(extension): use template for Edge certification notes 2026-10-06 17:49:34 +02:00
Tautvydas Derzinskas 84b4f5bd14 fix(extension): store imports in shared storage 2026-10-06 15:00:54 +02:00
Tautvydas Derzinskas c52554fe7e refactor: replace re-import with narrower fill-gaps 2026-10-06 14:46:30 +02:00
Tautvydas Derzinskas fd7c26a760 feat: handle download limit error gracefully 2026-10-06 07:26:48 +02:00
github-actions[bot] 9e61819453 chore(extension): release 1.3.0
# [thingport-grab-v1.3.0](https://github.com/TautvydasDerzinskas/Thingport/compare/thingport-grab-v1.2.0...thingport-grab-v1.3.0) (2026-10-05)

### Features

* **extension:** add loading state phrases for different operations ([0325f16](https://github.com/TautvydasDerzinskas/Thingport/commit/0325f16c8527bea78343f91f386c0c0a0d61d02a))
* **extension:** allow importing to new custom collections ([a5ac824](https://github.com/TautvydasDerzinskas/Thingport/commit/a5ac82411079f395db9bcf9f951b7c1df9f096c8))
* **extension:** improve loading messaging + make queue admin-only ([67a31cc](https://github.com/TautvydasDerzinskas/Thingport/commit/67a31cc94052fda9faf1daf831b6fbf5ce7b53e9))
* link import queue with an admin page and send-to-queue in the extension, plus update from source ([#6](https://github.com/TautvydasDerzinskas/Thingport/issues/6)) ([96da36a](https://github.com/TautvydasDerzinskas/Thingport/commit/96da36ae7999ab5c91bf076a727922a0dbdad0ec))
* pause guided MakerWorld imports on a CAPTCHA, and fix localized and long collection imports ([627a442](https://github.com/TautvydasDerzinskas/Thingport/commit/627a442d53a709f41e42bc508af7305aca5578a1))
2026-10-05 19:17:57 +00:00
Tautvydas Derzinskas a5ac824110 feat(extension): allow importing to new custom collections 2026-10-05 21:06:26 +02:00
Tautvydas Derzinskas 0325f16c85 feat(extension): add loading state phrases for different operations 2026-10-05 20:49:39 +02:00