Giter Site home page Giter Site logo

Comments (17)

jumde avatar jumde commented on August 14, 2024 2

@privacycg/chairs : This proposal is getting sufficient feedback from the community. We'd like to move this to a dedicated repository within @privacycg to get more feedback before we start working on the implementation. Explainer here: https://github.com/brave-experiments/js-membranes/

Let us (@snyderp and I) know if you have any questions or concerns.

from proposals.

hober avatar hober commented on August 14, 2024

This is really interesting, thanks!

What is the relationship between this and tc39/proposal-realms?

from proposals.

pes10k avatar pes10k commented on August 14, 2024

They're related, and you could use a lot of the same machinery, but realms would require existing code to be updated, to change some of its programming model.

Realms are about "isolated worlds", or ways of really knowing some code can't modify the external environment; this proposal is (effectively) a way for privileged code to impose access controls over a single environment.

from proposals.

jakearchibald avatar jakearchibald commented on August 14, 2024

Interesting! How do you decide which origin accessed the object?

// First party script /index.js
function runCallback(callback) {
  return callback();
}

function getLocation() {
  return window.location.href;
}

function getProperty(target, key) {
  return target[key];
}

// Third party script evil.com/index.js
// Who accesses the location in these cases?
runCallback(() => window.location.href);
getLocation();
getProperty(window, 'location');

Also, is there a security issue here? Currently you can't access the source of a third party script (although it's at risk due to spectre/meltdown).

// Third party script
function whatever() {
  const str = `Your script can't see this`;
  return str.slice(0, 1);
}

Will the access of str.slice(0, 1) give you a callback that lets you see str? You're accessing String.prototype.slice so it counts as something global.

from proposals.

pes10k avatar pes10k commented on August 14, 2024

@jakearchibald thanks for the questions! We're really eager for this kind of feedback, so its great to think through these kinds of questions, and see where the proposal could be tightened / corrected (or if we're going in some goofy direction).

As written, the spec would say that its the 3p script, 1p script, and 1p script doing those accesses, respectively. So, effectively, if the 1p script had a footgun like getProperty(), the 1p could pretty quickly shoot itself in the foot, but…

But in each case, here are the places where the membrane proposal would give you hooks (to prevent this kind of creep):

runCallback case

  1. get: hook in a proxy targeting evil.com would fire with window, undefined and evil.org
  2. get: hook in a proxy targeting evil.com would fire with window, location and evil.org
  3. get: hook in a proxy targeting evil.com would fire with window.location, href and evil.org

getLocation case

  1. get: hook in a proxy targeting first-party would fire with window, undefined and 1p origin (or some 1p indicating value)
  2. get: hook in a proxy targeting first-party would fire with window, location and 1p origin
  3. get: hook in a proxy targeting first-party would fire with window.location, href 1p origin

getProperty case

  1. get: hook in a proxy targeting evil.com would fire with window, undefined and evil.org
  2. get: hook in a proxy targeting first-party would fire with window, location and 1p origin

(note this is in the maximal, I want to mediate access to everything case)

from proposals.

jakearchibald avatar jakearchibald commented on August 14, 2024

Ohh, so you wouldn't see the accesses of runCallback, getLocation and getProperty? Is this assuming they're in the global module scope, rather than window.runCallback etc?

I guess if you wanted to do something about the other cases, you could provide a set of origins representing everything on the stack. Although that would be broken by anything async.

from proposals.

pes10k avatar pes10k commented on August 14, 2024

re whatever case (last thing), JS builtin globals is a really interesting question (grateful for the feedback already!)

We wouldn't want to target them (or might want some "yes and the JS builtins too" opt in). But that if someone was going to try and leverage this to get around things, ex:

const origSlice = String.prototype.slice;
let stolenDocRef;
String.prototype.slice = function (...args) {
   stolenDocRef = window.document;
   return origSlice.apply(this, args);
}

That'd trigger 3p tainted hooks for window, undefined and window, document, etc

from proposals.

jakearchibald avatar jakearchibald commented on August 14, 2024

Ah, ignore my comment about exposing the string. Since you can overwrite prototype methods you can already get access to str. Sorry for the noise.

from proposals.

pes10k avatar pes10k commented on August 14, 2024

Ohh, so you wouldn't see the accesses of runCallback, getLocation and getProperty? Is this assuming they're in the global module scope, rather than window.runCallback etc?

Yep, though (simplifying straw proposal) might be enough to say "3p can access window, but once it starts trying to grab references to anything document / Web API related, then hooks kick in. i.e. first parties should not use this as a replacement for protecting 1p JS defined state / structures, there are already ways of doing that (modules, closures, etc).

So if the first party defines window.getCookies => document.cookie, thats not a problem the proposal is trying to solve. There are already ways of solving that problem. Just for mediating access to document, etc, which doesn't have a good solution currently

from proposals.

jakearchibald avatar jakearchibald commented on August 14, 2024

Is there a way to define which property accesses this would protect, or would it just be a manually maintained list?

from proposals.

pes10k avatar pes10k commented on August 14, 2024

from proposals.

pes10k avatar pes10k commented on August 14, 2024

I've updated the spec with the following changes / clarifications:

  • More specific that the proposal targets web structures / documents / etc, and not all global state
  • Give straw-proposal for other types of information about the executing script that could be made available to the policy for decision making
  • Sever off the (simpler) question of how sites get the policy to the browser (which seems relatively simple, but distinct) from the main goal of the proposal; describing the policy decision points and goals

from proposals.

pes10k avatar pes10k commented on August 14, 2024

added further explainer text in FAQ section detailing how this proposal is fundamentally different from SES and similar "isolated worlds" approaches

from proposals.

jackfrankland avatar jackfrankland commented on August 14, 2024

I really like this proposal. I have some questions if I may:

  1. It seems like there's a scenario where two membrane proxies can be registered for the same origin. Would one have a preference over the other, or do they "layer" up in a particular order?
  2. I believe a motivating use case should be to allow third parties full access to a particular DOM element for the purpose of embedding content, without giving access to the rest of the DOM and limiting access to the global scope. I'm having a hard time seeing how to effectively achieve this using this proposal. Let me know if you'd like me to be more specific, in case you think this proposal should cover this use case.
  3. The document does mention performance, but if we're talking about hundreds or thousands of DOM nodes within a single-page application - by having JS around the native HTMLElement functions, it feels like there may be a significant performance consequence.

Cheers.

from proposals.

hober avatar hober commented on August 14, 2024

Adding to the agenda for our next call per offline conversation with @snyderp.

from proposals.

pes10k avatar pes10k commented on August 14, 2024

Hi @jackfrankland

Apologies for letting this drop, I missed a ping somewhere. Thanks for your questions / thoughts!

two membrane proxies can be registered for the same origin

I think you'd need multiple proxies being able to interact / stack here, in case (say) an extension and the site both wanted to restrict scripts.

allow third parties full access to a particular DOM element for the purpose of embedding content, without giving access to the rest of the DOM

There are a lot of ways you might enforce this. But here's a silly toy example:

    // Page
    <div>
        <!-- secret stuff -->
        <section>
            <input type="text" name="ccn">
        </section>
        <!-- the script should be able to see this stuff -->
        <section id="only-for-the-pw-lib">
            <div id="password-strength-feedback-response"></div>
            <input type="password" name="password">
        </section>
    </div>
    <script src="https://example.org/js/pw-strength.js"></script>

    // Membrane
    const htmlElmProto = window.HTMLElement.prototype;
    let trustedElementRoot;
    const isParentOf = (parentElm, possibleChildElm) => {
        // some code that just walks up the tree and returns true
        // if possibleChildElm is in the tree below parentElm, and
        // otherwise false.
    }

    window.registerMembraneProxy(["example.org"], {
        get: (target, prop, scriptInfo) => {
            if (trustedElementRoot === undefined) {
                trustedElementRoot = document.getElementById("only-for-the-pw-lib");
            }

            // We only want the script to touch html elements…
            if (htmlElmProto.isPrototypeOf(target) === false) {
                return null;
            }

            // and only HTML elements in the part of the document we want it to
            // access.
            if (isParentOf(trustedElementRoot, target) === false) {
                return null;
            }

            // Otherwise do the thing…
            return Reflect.get(target, prop);
        }
    })

The above example is toy, and isn't meant to be bullet proof, just concise enough to demonstrate one possible way you'd use the machinery. Tooling would make all this much nicer, but I think the capabilities in the spec are what's needed to build on.

performance consequence

Thats def possible. Proxies are (really!) surprisingly fast, but im sure the overhead wouldn't be zero. Good tooling to help folks build tight policies would help, but I take your point, that this is def not a zero-cost proposal.

from proposals.

hober avatar hober commented on August 14, 2024

@jumde wrote:

@privacycg/chairs : This proposal is getting sufficient feedback from the community. We'd like to move this to a dedicated repository within @privacycg to get more feedback before we start working on the implementation. Explainer here: https://github.com/brave-experiments/js-membranes/

Let us (@snyderp and I) know if you have any questions or concerns.

We've spun up a repo for you: https://github.com/privacycg/js-membranes

Could you and @pes10k double check you have read-write access to it? I think you may need to accept your invitation to join the Privacy CG GitHub org first, @jumde. Pete already has. Go here to do so: https://github.com/privacycg

from proposals.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.