Chrome Manifest v3 extensions may be rejected due to "obfuscated code"
follow-up to https://github.com/PostHog/posthog-js/issues/1394
that issue is very long already so I want to have a little more space to breathe for what is a separate problem that will have a different solution
see https://github.com/PostHog/posthog-js/issues/1394#issuecomment-2371497392 from @oliverdunk
his comment carried here:
I took a quick look and didn't see this code present anymore, We had a lot of discussion about this internally, which is why your review took longer than normal - apologies for that. In summary: Creating a worker using a blob URL (this is what the base64 string in your rejection email is used for) violates the script-src policy we intend to apply to MV3 extensions. Due to a Chrome bug, this currently works and would only be caught during review. However, we would like to change that in the future. Once that bug is fixed, this would be dead code in violation of our policies. Our usual rule is to still enforce on this code as (while it may be less likely in this case) we have definitely seen code that looks like dead code become active across updates and used maliciously. Given the above, and that understanding this code is quite hard during review, we have decided that this does violate our policies.
see also
from https://github.com/PostHog/posthog-js/issues/1394#issuecomment-2370278219
other context
- "(ultimately a dependency of PostHog seems to be using npmjs.com/package/rollup-plugin-web-worker-loader)" https://github.com/PostHog/posthog-js/issues/1394#issuecomment-2346028323
- rrweb code has https://github.com/rrweb-io/rrweb/issues/1377
first step is likely to get updated to latest rrweb so we can be sure we're not chasing shadows https://github.com/PostHog/posthog-js/pull/1276
Sorry if this question has already been asked but will session replay currently work with a chrome extension V3?
- Unable to use with Manifest v3 due to remote code executionΒ #1394 (comment)
Unfortunately it will not pass the review by the Chrome Extension team yet check out the discussion here
https://github.com/PostHog/posthog-js/issues/1394#issuecomment-2399245692
@pauldambra any new updates on the progress of this issue? We really missing having the session recording observability in our chrome extension.
@pauldambra any new updates on the progress of this issue? We really missing having the session recording observability in our chrome extension.
Same question, I've paused session recording for a couple of weeks and really need it π @pauldambra
the rrweb upgrades took a bunch of attention so we haven't looked at this yet (i'll make the standard reminder that PRs are welcome if other folk have time to look at it - but i appreciate this is fairly deep in the guts of your dependencies dependency π )
it's been logged here already https://github.com/rrweb-io/rrweb/issues/1578 without any engagement :/
pls prioritize
ok, pulling on this thread... it might be possible to fix this and avoid needing to remove Canvas recording support
we can test if https://github.com/rrweb-io/rrweb/pull/1448 would remove this obfuscated code from the bundle in posthog's usage of rrweb, and if we see that folk's extensions start to pass google's checks, then we can prompt the rrweb maintainers and get this fixed upstream so everyone benefits
full disclosure to save people following all the links, that is a PostHog PR to rrweb implementing a change from Sentry's fork of rrweb they they offered to contribute https://github.com/rrweb-io/rrweb/issues/1376. in both cases folk were only looking at bundle size since that predates google's changes to the review process.
ok, pulling on this thread... it might be possible to fix this and avoid needing to remove Canvas recording support
we can test if rrweb-io/rrweb#1448 would remove this obfuscated code from the bundle in posthog's usage of rrweb, and if we see that folk's extensions start to pass google's checks, then we can prompt the rrweb maintainers and get this fixed upstream so everyone benefits
full disclosure to save people following all the links, that is a PostHog PR to rrweb implementing a change from Sentry's fork of rrweb they they offered to contribute rrweb-io/rrweb#1376. in both cases folk were only looking at bundle size since that predates google's changes to the review process.
let me know how i can publish this to the google store we can do this right away to test
Thanks for looking into this @pauldambra. I'm going to remove posthog recording right now to get things published.
Yep, unfortunately and super frustratingly that's the only solution at the moment. We really hate that that's the case
We just fixed this upstream with this PR: https://github.com/rrweb-io/rrweb/pull/1568
Specifically this fixes it in the bundling step as long as the DISABLE_WORKER_INLINING=true flag is set (which we only run while building the extension): https://github.com/rrweb-io/rrweb/blob/d09f561073304b2fcbd426576de1f03d46241e55/vite.config.default.ts#L164-L176
Also see the release.yaml for how this is used to release a new version of the extension to the Chrome store.
ok, since the rrweb solution is a separate bundle. i think the shortest fix (and since it's confusing for folk to pick the correct items to build to avoid other google chrome store rejections) is for us to make a separate extensions bundle
i'm going to put this on my to-do list but it's going to be next week at the earliest π
Question: why do this as a post-step job in CI, if this could be solved simply by bumping vite to ^6.0.1?
https://github.com/rrweb-io/rrweb/issues/1578#issuecomment-2612855699
interesting comment on the rrweb side... and great research π
for posthog why do it as a post step is because we're not building rrweb :)
if this can be fixed upstream then i'm very happy to do no extra work
Is there a solution for this yet? My extension has just been rejected for the same thing after importing: "import posthog from "posthog-js/dist/module.full.no-external";"
I only need analytics and surveys without external dependencies. Is there a way I can only import these two features and have webpack not include rrweb from session replay?
I only need analytics and surveys without external dependencies. Is there a way I can only import these two features and have webpack not include rrweb from session replay?
You can import posthog-js/dist/module.no-external and then posthog-js/dist/surveys to get only analytics and surveys
https://posthog.com/docs/libraries/js
@isak102 thank you, I'll give that a go.
@isak102 this solution worked for me, thank you π
we've been testing an internal build of rrweb (the recorder tool) that I believe will no longer trigger this warning - but we don't have a chrome extension to test with
if anyone is willing to bundle posthog-recorder instead of recorder in their extension to test that would be amazing!
so instead of
import "posthog-js/dist/recorder.js"
you would
import "posthog-js/dist/posthog-recorder.js"
welcome to email paul AT posthog DOT com or let me know here
@oliverdunk is someone at google able to validate the posthog-recorder.js I think it won't trigger the obfuscated code π€
@pauldambra thanks and good to hear that. i will pack my chrome extension dmooji today and ship it with posthog-recorder.js, but it will take 1-3 days for reviewing. can you please share more instruction about how to implement posthog-recorder.js?
Before, I import posthog like this below to prevent remote code warning.
import posthog from "posthog-js/dist/module.full.no-external";
if (process.env.PLASMO_PUBLIC_POSTHOG_API_KEY) {
try {
posthog.init(process.env.PLASMO_PUBLIC_POSTHOG_API_KEY, {
api_host: "https://app.posthog.com",
persistence: "localStorage",
autocapture: true,
person_profiles: "always",
disable_session_recording: false,
capture_pageview: true,
loaded: (posthog) => {
posthog.register({
full_url: window.location.href,
domain: window.location.hostname,
});
},
});
} catch (err) {
log.error(err);
}
}
hey @giftedunicorn it'll be easier once we know we can ship this internal build of the recorder for now the "full" package already includes the external build of the recorder that triggers the error
so it would look (something) like
// no external so we don't trigger the external code loading static analysis
import posthog from './node_modules/posthog-js/dist/module.no-external.js';
// not the "full" package so that we can choose which recorder
import './node_modules/posthog-js/dist/array.no-external.js';
// NB IMPORTING THIS NEW BUILD OF THE RECORDER
import './node_modules/posthog-js/dist/posthog-recorder.js';
// and then any other extensions you want to add like error tracking or surveys
hey @pauldambra
what about if we are using the "posthog-js/react" lib as follows:
import { PostHogProvider } from "posthog-js/react"; import './node_modules/posthog-js/dist/posthog-recorder.js';
<PostHogProvider apiKey={import.meta.env.VITE_PUBLIC_POSTHOG_KEY} options={{ api_host: import.meta.env.VITE_PUBLIC_POSTHOG_HOST, persistence: "localStorage", disable_external_dependency_loading: true, capture_pageview: true, disable_session_recording: false, }} >
How could I integrate the posthog-recorder in this setup?
hey @giftedunicorn it'll be easier once we know we can ship this internal build of the recorder for now the "full" package already includes the external build of the recorder that triggers the error
so it would look (something) like
// no external so we don't trigger the external code loading static analysis import posthog from './node_modules/posthog-js/dist/module.no-external.js'; // not the "full" package so that we can choose which recorder import './node_modules/posthog-js/dist/array.no-external.js'; // NB IMPORTING THIS NEW BUILD OF THE RECORDER import './node_modules/posthog-js/dist/posthog-recorder.js'; // and then any other extensions you want to add like error tracking or surveys
I can confirm now the posthog-recorder.js passed the google extension reviewing and no more obfuscated code warning any more.
I can also confirm our chrome extension successfully passed and is receiving session recordings successfully π π
That's amazing news! Thanks for testing and confirming π
Will finalise the rollout to switch to this bundle