20,091 Matching Annotations
  1. Feb 2021
    1. You have to guess when the data is not likely to be needed in memory. It can't be too short that the cache is useless, and too long that you'll get a memory leak.
    1. One reason Turbolinks sites seem faster than traditional web apps is because of its cache. However, the cache can be a source of great frustration. Many of the edge cases we're going to discuss involve the cache in some way.
    2. Now let me ask you, do you write JS for a single page application differently from a "traditional" web application? I sure hope you do! In a "traditional" application, you can get away with being sloppy because every time the user navigates to a new page, their browser destroys the DOM and the JavaScript context. SPAs, though, require a more thoughtful approach.
    3. where's the code that unloads the table-sorter plugin when the page unloads? There isn't any. There didn't need to be back in the day because the browser handled the cleanup. However, in a single-page application like Turbolinks, the browser doesn't handle it. You, the developer, have to manage initialization and cleanup of your JavaScript behaviors.
    4. When people try to port traditional web apps to Turbolinks, they often run into problems because their JS never cleans up after itself.
    5. All Turbolinks-friendly JavaScript needs to: Initialize itself when a page is displayed Clean up after itself before Turbolinks navigates to a new page.
    6. For new projects, I would recommend using Webpack, along with perhaps a lightweight framework like Stimulus.
    7. Turbolinks is a Single-Page Application Turbolinks doesn't just give you some of the benefits of a single-page app. Turbolinks is a single page app. Think about it: When someone visits your site, you serve them some HTML and Javascript. The JavaScript takes over and manages all subsequent changes to the DOM. If that's not a single-page app, I don't know what is.
    8. Well, I'm glad they did, because Turbolinks is a much better piece of software than jquery-pjax ever was. It's actively maintained and doesn't require jQuery at all! So we're one step closer to our dream of ditching $.
    9. Now if you think about it, PJAX sounds a lot like Turbolinks. They both use JS to fetch server-rendered HTML and put it into the DOM. They both do caching and manage the forward and back buttons. It's almost as if the Rails team took a technique developed elsewhere and just rebranded it.
    10. In 2025 we plan to

      Surely this is a typo and should have said 2020? Nobody would make such a specific tech plan for 5.5 years in the future ... would they?

    11. we plan to migrate to Angular 1, and we'll finish out the decade on React

      Wrong direction: I'd recommend migrate from Angular to React.

    12. The only problem is that our PJAX library is no longer maintained and was preventing us from updating jQuery (ugh). So it had to go.

      https://github.com/MoOx/pjax doesn't say it's no longer maintained (though hasn't been updated in 2 years), and does say that it doesn't use jQuery. Oh well.

    13. There's an approach we've been using for years that lets us have our cake and eat it too. It's called PJAX, and its big idea is that you can get SPA-like speed without all the Javascript. When a user clicks a link, the PJAX library intercepts it, fetches the page and updates the DOM with the new HTML.
    14. Our app is mostly about displaying pages of static information. We crunch a lot of data to generate a single error report page.
    15. Honeybadger isn't a single page app, and it probably won't ever be. SPAs just don't make sense for our technical requirements.
    1. So the hard and unsolvable problem becomes: how up-to-date do you really need to be?
    2. After considering the value we place, and the tradeoffs we make, when it comes to knowing anything of significance, I think it becomes much easier to understand why cache invalidation is one of the hard problems in computer science

      the crux of the problem is: trade-offs

    3. why a company like Facebook invests so much research and engineering into the network performance of things as seemingly trivial as notifications.
    4. the 2 hardest problems in computer science are essentially the 2 hardest problems of life in general, as far as humans and information are concerned.
    5. The non-determinism is why cache invalidation — and that other hard problem, naming things — are uniquely and intractably hard problems in computer science. Computers can perfectly solve deterministic problems. But they can’t predict when to invalidate a cache because, ultimately, we, the humans who design and build computational processes, can’t agree on when a cache needs to be invalidated.
    6. I like the answers already given, but I think they both could use an even more top-level, generalized explanation.
    7. Cache invalidation is hard because: Everything in life we want to know, changes.Those changes are non-deterministic.
    8. you began by first finding out if your crush was already in a relationship. If so, you then did what you could in your power to have the most most up-to-date information on their relationship status. The downside of outdated data is self-evident: you want to move in at the first sign of the current relationship dissolving.
    9. Sometimes humorously extended as “cache invalidation, naming things, and off-by-one errors.”
    1. There’s only one hard thing in Computer Science: human communication. The most complex part of cache invalidation is figuring out what the heck people mean with the word cache. Once you get that sorted out, the rest is not that complicated; the tools are out there, and they’re pretty good.
    2. Cache and caching are some of the most ambiguous words in the IT world, and that’s because we can have multiple types of caching working in parallel and affecting content independently.
    1. Instead of trying to educate everyone on the complexities of copyright law, we’d rather make our intentions clear with this simple statement:
    2. I think you want a symbol with a circle around it, like the circle around the C in ©. That way the association with the copyright symbol is clear.
    3. But the circle on its own doesn’t seem to be available as a nonspacing diacritic in Unicode. Bugger.
    4. Creating more legally binding licenses and contracts just perpetuates the problem of law – a.k.a. state force – intruding where it doesn’t belong.
    5. That ♡copyheart isn’t a legally binding license is not a bug – it’s a feature!
    6. We really don’t think laws and “imaginary property” have any place
    1. This is not a game.It's just a thing.It's nothing to do with cash.Luckily, it's free.Don't pay a dime in this.it's not a game.It's just... more.It's just more.Not in a good way.Nor in a bad way.Sometimes more is just more.This is more. More snore.Is it a good snooze?You decide.I recommend you decide for yourself.After you give it a try.It's free.A free what though?This is not a game.
    1. please, for the love of god do NOT use Mint as a source of inspiration for a derivative distro. If you like Cinnamon or Mate, fine, but holy CHRIST do not let your infrastructure get as criminally sloppy as Mint's. No unholy mixing of Debian and Ubuntu debs into some kind of Frankenbuntu, no namespace collisions, no ... well, no being Mint in general, please!Ideally, I really, really hope you'll continue to support Ubuntu as a primary platform, regardless of what you do with Pop!_OS. But hooboy, do not turn into another Mint, please.
    2. Everyone here wears many hats

      links to image of someone literally wearing many hats

    3. We're small, but we're efficient. We can do with the number of people we have what would take twice the workforce of other companies. Everyone here wears many hats, and that allows us to cover a lot of ground without needing as many people.
    4. when it comes to personal machines, I expect them to just work so I can work.
    5. Not to mention 80% of our sales are laptops and desktops running, you guessed it, a Linux desktop. So, unlike Red Hat and Canonical, we live or die based on how good that experience is.
    6. If it was remotely possible to get Davinci Resolve running that would be incredible (and bring a lot of video people I think)
    7. We do know what our customers ask us for: powerful desktops and laptops that work with them in their creative endeavors. And we know that Canonical is no longer interested in catering to them. So we're going to try and step up.
    8. the most productive environment possible for people that use their computer to create.What is a productive environment?How do you measure productivity in an operating system environment?How do you compare YOUR distribution to other distributions when it comes to productivity?Is the way in which 'people that use their computer to create' (creators) the same across all professions and activities?Does a photographer have the same requirements for a productive environment as a software engineer?Why do you think your distribution will be the best for delivering a productive environment than any other Linux distribution?
    1. This gives them a slight edge but that’s nothing substantial because those fixes eventually reach Ubuntu.
    2. Technically, it isn’t a part of the comparison internally but it is a factor that some users care for.
    3. Pop!_OS has its own official PPA which is enabled by default.
    1. It’s always about the money… Fish got’a swim, birds got’a fly, and development has to have money. If you think otherwise you’re a fool!
    2. Considering Canonical has pulled resources from this project, the path for continued third-party development of Unity will not be easy. It is my hope that they are successful and can become another shining example of the power of forking, like the MATE project.
    1. Pop!_Os makes some improvements on Ubuntu especially for gaming and coding. There are newer drivers and some coding related things are easier to setup.
    2. Get off systemd, and enter the world of chroot.
    3. And then think about if you want a rolling release, or a fixed release. Although all the distros you mentioned are on the fixed release side.
    4. Think about how much you want to customize the desktop environment(DE), and whether you know how to do so. Pick a distro that has the DE you like.
    5. There is no best distro. All of them are more or less the same.
    6. When people talk about "beginner distros" they mean distros that are no hassle to get started, it doesnt mean they are somewhat inferior or less capable.
    7. And honestly, most people prefer the no hassle, especially after wasting too much time dabbling with distros that are "for advanced users" troubleshooting all kinds of dumbass problems that just worked out of the box in many other distros.
    1. I chose 18.04 because it's the latest LTS version, and I'm not keen on updating my OS every year or so. (I like getting things stable and not having to worry for a while)
    2. considering PopOS is trying to tackle Ubuntu they really need their dual-boot setup to be a lot less tedious
    3. Couldn't agree more, the whole fuss about POP OS is overrated. I think it started because of a video on Linus tech tips, which listed Pop OS as one of the best solutions for Linux gaming. But I think that running Ubuntu + some Linux knowledge to install the proprietary driver is a better solution imo.
    4. if PopOS! really wants to be what Ubuntu was 10 years ago they need to step up and make dual booting easier.
    5. Instead of resizing the existing Widnows EFI System partition of size 100 mb, Can't I just create a new EFI system partition of 500 mb FAT32 for bootloader and linux only related stuff?
    6. Instead of resizing Windows efi partition, I created a new one for pop os as well. So now my system has two different efi partitions. No chance of any messing up.
    7. I tried it but the tool wouldn't let me resize the EFI partition
    8. If would recommend you create a bootable Windows 10 USB from the MS website and reinstall the PC with a clean Windows installation so you have the same Windows installation as shown in the video. Also, you'll be a lot happier with all the bloatware removed.
    9. The part where you want to add 2 EFI partitions is not advisable. It seems that Windows doesn't really like this, of you are dual booting multiple Linux installs it might work. But it is always recommended to use only 1 EFI partition per disk. Hope this helps. :)
    1. You don't necessarily have to resize Windows' EFI partition. You can have multiple EFI partitions.
    2. When I started Pop!_Planet, I launched it because I saw a need for a centralized community for Pop!_OS. To be frank, I never expected the level of popularity it has achieved. Over the last year, we have gone from under 50 users, to almost 400 users. That's awesome! However... it also comes with a downside. We are rapidly running out of disk space on our server, and the bandwidth costs go up every month. Pop!_Planet is not affiliated with System76 in any way, and is funded completely out of pocket. From day one, I said that I'd never use on-site ads (I hate them as much as you do), so the only monetization we get is through donations. Right now, the donations we receive don't even cover our overhead. I know that most users will ignore this message, and that's ok. However, if even a few of our users are willing and able to donate a few dollars to help offset our expenses, it would be greatly appreciated.
    1. Make a 512MB fat32 partition during manual/custom PopOS install.Select its role as: "/boot/efi" in the PopOS installer.When the OS is installed, type sudo apt install refind and then it should automatically start the installer else type sudo refind-install. This will install rEFInd to your /boot/efi path.
    2. this method has a great looking dual boot menu that auto-remembers your last used OS, making dual booting convenient
    1. Switching to Pop!_OS From Apple If you are coming from Apple’s operating system using Pop!_OS for the first time, we can help make the transition smoother.
    2. Switching to Ubuntu from Apple If you are coming from Apple’s operating system and just using Ubuntu for the first time, we can help make the transition a little smoother.
    1. Disable Secure Boot. Security technologies included in UEFI such as Secure Boot can be a blocker and prevent the system from booting external storage sources. Disabling Secure Boot, temporarily—normally accessible under the security menu or tab—will often resolve this.
    1. Windows and Linux store their time in the BIOS differently, this will cause your clock to be desynchronized when you switch from one OS to the other. The easiest solution for it is to fix it in Linux, forcing it to work the same way as Windows. You can do this through the terminal:
    2. Note that Windows updates may occasionally turn this setting back on without asking, so if you are unable to boot into Pop!_OS, check this setting first. (If the checkbox for ‘Turn on fast startup’ is grayed out, you can enable it by click ‘Change settings that are currently unavailable’ near the top of the power buttons settings page)

      making it harder to do something preventing from shooting self in foot

    1. Jan 2021. I use a small, dedicated enterprise grade SSD as a swap drive. These enterprise drives can be bought for as little as $80 for 240GB right now, and are 3D nand with load leveling and other valuable improvements for swap. By using the drive only for swap, you pretty much guarantee it won’t affect your expensive terabyte level data drive should it fail, and you still get the performance of SSD. Estimates for very heavy use are about 2 1/2 years.
    1. Any progress on this issue?
    2. Sean, do you think someone can take a look at this? It's biting a lot of people and makes .or pretty much useless if you want the .or query to use a simple join, which is a pretty common use case. There are 57 likes in this issue alone.
    3. A.joins(:b) .where( A.arel_table[:something_a].eq('xxx').or(B.arel_table[:something_b].eq('yyy')) )
    4. I was wondering what is the status of this issue? The PR that fixes the problem is rejected but this issue is still open, so is it going to be fixed or is it intended behaviour?
    5. I recall that we wanted to reserve the right to make it more conservative in the future
    6. That's covered by "they must differ only by #where"
    7. but if .or() throws an error then I'm back to the bad old days of using to_sql
    1. You can write the query in this good old way to avoid error
    2. According to this comment you might want to override the structurally_incompatible_values_for_or to overcome the issue: def structurally_incompatible_values_for_or(other) Relation::SINGLE_VALUE_METHODS.reject { |m| send("#{m}_value") == other.send("#{m}_value") } + (Relation::MULTI_VALUE_METHODS - [:eager_load, :references, :extending]).reject { |m| send("#{m}_values") == other.send("#{m}_values") } + (Relation::CLAUSE_METHODS - [:having, :where]).reject { |m| send("#{m}_clause") == other.send("#{m}_clause") } end
    3. Also there is always an option to use SQL: @items .joins(:orders) .where("orders.user_id = ? OR items.available = true", current_user.id)
    1. # Returns a new relation, which is the logical union of this relation and the one passed as an # argument. # # The two relations must be structurally compatible: they must be scoping the same model, and # they must differ only by #where (if no #group has been defined) or #having (if a #group is # present). Neither relation may have a #limit, #offset, or #distinct set.
    1. If you need your grid to utilize a gap between columns / rows, you won't be able to use the gap property when using this method. You'd instead need to resort to some negative margin manipulation to handle the extra gap space.
    2. without grid-template-rows layout properties getting passed over to the next row
    1. You use grid-area, so the place for the side nav is allocated at start. If you hide (or even delete) the side nav, that won't change anything about this. You have to do a little trick: Set the width for the first column to 0 and change the grid-gap because otherwise you will have a (not needed) gap at the left.
    1. Adding backgrounds and borders does feel like a missing feature of the CSS Grid specification and one which the Working Group have discussed along with many members of the community (the discussion thread is on GitHub).
    2. This gives me the layout with the full-width image and two sections of content placed; however, if I add the background to the sections, it will stop above the row-gap between section and the full-width image.
    3. With Grid and generated content, we can add a line either side of our heading without adding any additional markup. The line will grow and shrink according to available space
    4. The key phrase here is “children of a grid container.” The specification defines the creation of a grid on the parent element, which child items can be positioned into. It doesn’t define any styling of that grid, not even going as far as to implement something like the column-rule property we have in Multi-column Layout. We style the child items, and not the grid itself, which leaves us needing to have an element of some sort to apply that style to.
    1. But all of these attempts misunderstand why the Open Source ecosystem is successful as a whole. The ecosystem of fairly standard licenses provides a level playing field that allows collaboration with low friction, and produces massive value for everyone involved – both to those that contribute and to those that don't. It is not without problems (there are many essential but unsexy projects that are struggling with funding), but introducing more friction won't improve the success of this ecosystem – it will just lead to some parts of the ecosystem to break off.
    2. There have also been extensions for suggestions towards more “ethical” licensing, to prevent certain undesirable uses.
    3. Part of me thinks that open source can be more rewarding to the creators/contributors. But maybe the real contribution is the permanent addition to the tools available to humanity, and if you have the wits, you can make a decent business out of it without tainting open source.
    4. Selling proprietary software is difficult when there is so much gratis Open Source software around.
    5. For a sufficiently successful and industry-relevant open source project, it's possible for the main developers to earn a living e.g. by selling related consulting services.
    6. It turns out that creating and using Free Software is not just good to individuals, but for businesses as well, for example by building upon publicly available components and by collaborating shared software. The term Open Source is a business-friendly rebranding of the Free Software concept. This line of thought was also widely successful, e.g. Firefox/Mozilla was an open sourcing of Netscape software.
    7. Foundations like Apache or Eclipse also create massive value across the industry by getting multiple companies to collaborate on “neutral ground”.
    1. Ensure that there can only be four items per row: grid-template-columns: repeat(auto-fill, minmax(20%, 1fr)); grid-gap: 10px; With 20% minimum width per item, and a grid gap (of any length), there can never be more than four items per row.
    1. Because of the way the CSS “or” operator works, I wouldn’t be able to mix the retina conditions with other expressions since a (b or c) would be compiled into (a or b) c and not a b or a c.
    1. auto (i.e. minmax(auto, max-content))
    2. Note: auto track sizes (and only auto track sizes) can be stretched by the align-content and justify-content properties.
    3. Is a keyword that is identical to maximal content if it's a maximum. As a minimum it represents the largest minimum size (as specified by min-width/min-height) of the grid items occupying the grid track.
    1. If no end line value is declared, the item will span 1 track by default.
    2. The values represent the track size, and the space between them represents the grid line.
    3. When you use this syntax the lines on either end of the areas are actually getting named automatically.
    4. Notice that you’re not naming lines with this syntax, just areas.
    5. The syntax itself provides a visualization of the structure of the grid.

      What is this an example of? self-referencing? self-presentation? duality?

    6. justify-content Sometimes the total size of your grid might be less than the size of its grid container. This could happen if all of your grid items are sized with non-flexible units like px. In this case you can set the alignment of the grid within the grid container.
    1. this issue is rather about styling the the cells and areas
    2. This idea is not new, there are reference books which teach the use of grid layout, I haven't seen a single book that doesn't show a grid overlay as part of the process.
    3. a designer / developer / designoper is able to create a grid overlay which would act as design reference.
    4. the author should be able to style area boxes
    5. proposes adding a grid-cell pseudo so you can add (responsive) decorative elements to grids without having to add empty elements to your page.
    6. #grid::grid-area(1 / 2 / 3 / 4) { background-color: red;
    1. I hope we see new CSS capabilities arise that allow this sort of effect without the need for trickery.
    2. When you generate before- and after-content pseudo-elements, Grid treats them as actual elements and makes them grid items.
    3. The first problem is that if you ever remove an item, there will be a big black block in the layout. Maybe that’s OK, but more likely it isn’t. The second problem is that grid containers do not, by default, shrink-wrap their items. Instead, they fill out the parent element, as block boxes do. Both of these problems are illustrated in Figure 6.
    4. Since CSS doesn’t (yet) offer a way to style grid cells, areas, or tracks directly, we have to stretch elements over the parts we want to style independently from the elements that contain content.
    5. I use <b>s for the decorative portions of the layout because they’re purely decorative elements. There’s no content to strongly emphasize or to boldface, and semantically a <b> isn’t any better or worse than a <span>. It’s just a hook on which to hang some visual effects. And it’s shorter, so it minimizes page bloat (not that a few characters will make all that much of a difference). More to the point, the <b>’s complete lack of semantic meaning instantly flags it in the markup as being intentionally non-semantic. It is, in that meta sense, self-documenting.
    6. div:nth-of-type(3n+1) { grid-column: 1; } div:nth-of-type(3n+2) { grid-column: 2; } div:nth-of-type(3n+3) { grid-column: 3; } div:nth-of-type(-n+3) { grid-row: 1; }
    7. The 1 / -1 means “go from the first grid line to the last grid line of the explicit grid”, regardless of how many grid lines there might be. It’s a handy pattern to use in any situation where you have a grid item meant to stretch from edge to edge of a grid.
    8. They likely won’t have any content, making them a sort of structural filler to spackle over the gaps in Grid’s capabilities.
    9. Just like in flexbox, this will move the displayed grid items out of source order, placing them after the grid items that don’t have explicit order values.
    10. #ttt > * { border: 1px solid black; border-width: 0 1px 1px 0; display: flex; /* flex styling to center content in divs */ align-items: center; justify-content: center; } #ttt > *:nth-of-type(3n) { border-right-width: 0; } #ttt > *:nth-of-type(n+7) { border-bottom-width: 0; }
    1. This nav bar by Chris Coyier is a great example of something that makes more sense as a flexbox than grid.
    2. Flexbox and grid play well together, and are a huge step forward from the float & table hacks they replace.
    3. Flexbox's strength is in its content-driven model. It doesn't need to know the content up-front. You can distribute items based on their content, allow boxes to wrap which is really handy for responsive design, you can even control the distribution of negative space separately to positive space.
    4. Flexbox: content dictates layout
    5. Grid: container dictates layout
    1. .box1 { grid-column-start: 1; grid-column-end: 4; grid-row-start: 1; grid-row-end: 3; } .box2 { grid-column-start: 1; grid-row-start: 2; grid-row-end: 4; }
    1. the difference is exactly like block and inline-block ... if you use inline-grid with sibling elements they will be placed in the same line unlike grid ... so here you change to grid also since each element is inside a grid area alone
    1. Although one thing you want to avoid is using frames in such a manner that the content of the site is in the frame and a menu is outside of the frame. Although this may seem convienient, all of your pages become unbookmarkable.
    1. There is one situation where iframes are (almost) required: when the contents of the iframe is in a different domain, and you have to perform authentication or check cookies that are bound to that domain. It actually prevents security problems instead of creating them. For example, if you're writing a kind of plugin that can be used on any website, but the plugin has to authenticate on another domain, you could create a seamless iframe that runs and authenticates on the external domain.
    2. Iframes can have similar issues as frames and inconsiderate use of XMLHttpRequest: They break the one-document-per-URL paradigm, which is essential for the proper functioning of the web (think bookmarks, deep-links, search engines, ...).
    3. The most striking such issue is probably that of deep linking: It's true that iframes suffer from this to a lesser extent than frames, but if you allow your users to navigate between different pages in the iframe, it will be a problem.
    4. never care and try to understand design standards
    5. If you're creating an actual, informational web page, stick to frameless HTML, CSS and unobstrusive JavaScripts and keep in mind that the page should still be usable with scripting disabled.
    1. I normally try to figure out if that's a good solution for the problem before resorting to iframes. Sometimes, however, an iframe just does the job better. It maintains its own browser history, helps you segregate CSS styles if that's an issue with the content you're loading in.
    2. Yeah, this is one of those cases where it's not a "yes or no" type answer.
    1. that's a point, but I would say the opposite, when entering credit card data I would rathre prefer to be entirely in the Verified By Visa (Paypal) webpage (with the url easily visible in the address bar) rather that entring my credit card data in an iframe of someone's website.
    2. Then recently I was shopping at the John Lewis website, and they brought up the Verified By Visa page in an iframe - wonderful! I'm still looking at the John Lewis site, and all that's happening is I'm being asked for my Verified By Visa password - no problem. Although as a web developer I know that there's no technical difference between that and a plain old redirect-there-redirect-back, the user experience is so much better!
    3. remember that for each loaded iFrame, a DOM is created, HTML requests are made and document wrappers are instantiated, eating memory and bandwidth in the process
    4. Multiple answers are great. Check out all of them, not just the accepted one.
    1. Owning a blog or website involves two separate pieces, your domain and your host.
    2. Keep your domain in one place. If you ever get mad at your web host and decide to move your site, you’ll also probably want to transfer your domain if it’s registered with the old host. Domain transfers can be annoying, time-consuming, and confusing. But if you’ve registered the domain elsewhere, you don’t have to do anything except update your DNS settings to point to the new host.
    3. It’s kind of like putting a SIM card in a cell phone – the SIM card tells that phone, “Hey, you work with this particular phone number now.” Just like you can switch out a phone’s SIM card and make the phone work with a different phone number, your domain can be set to work with a different web hosting service.
    1. The main advantage of reverse proxies is unification. You no longer have to redirect visitors off-site or bounce them around between two sites. This disorganization can get confusing and takes away from a brand’s credibility and professionalism.
    1. As soon as you're displaying content from another domain, you're basically trusting that domain not to serve-up malware. There's nothing wrong with iframes per se. If you control the content of the iframe, they're perfectly safe.
    2. If you teach your users to trust that URL bar is supposed to not change when they click links (e.g. your site uses a big iframe with all the actual content), then the users will not notice anything in the future either in case of actual security vulnerability.
    3. And if there's a suitable vulnerability, it might be possible to trigger it even without using <iframe>, <img> or <a> element, so it's not worth considering for this issue.
    4. IFRAME element may be a security risk if any page on your site contains an XSS vulnerability which can be exploited
    1. hilarious sarcasm

    2. My goal (as it turns out) is simply to point out that any site that includes third party code is alarmingly vulnerable, in a completely undetectable way.
    3. So what’s the point in a post like this? Is it just me pointing and saying “ha, you’re a sucker!”.No, not at all. (Well, it was to start with, but then I realised I’m a sucker too, so I changed my tune.)
    4. I have a Content Security Policy!Oh, do you now.And did somebody tell you that this would prevent malicious code from sending data off to some dastardly domain? I hate to be the bearer of bad news, but the following four lines of code will glide right through even the strictest content security policy.
    5. it is very difficult to spot shenanigans in obfuscated code, you’ve got no chance.
    6. But I’m afraid it’s perfectly possible to ship one version of your code to GitHub and a different version to npm.
    7. The point is, just because you don’t see it, doesn’t mean it’s not happening. It’s been more than two years and as far as I know, no one has ever noticed one of my requests. Maybe it’s been in your site this whole time
    8. Also the URL looks a lot like the 300 other requests to ad networks your site makes.
    9. I’d notice the network requests going out!Where would you notice them? My code won’t send anything when the DevTools are open (yes even if un-docked).I call this the Heisenberg Manoeuvre: by trying to observe the behaviour of my code, you change the behaviour of my code.
    10. I’m harvesting credit card numbers and passwords from your site. Here’s how.