Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix(gatsby-plugin-utils): path pieces too long and url safe base64 encoding #35160

Merged
merged 22 commits into from
Apr 6, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
32 changes: 12 additions & 20 deletions e2e-tests/contentful/cypress/integration/gatsby-image-cdn.js
Expand Up @@ -15,28 +15,20 @@ describe(`gatsby-image-cdn urls`, () => {
it(`creates a proper gatsby image cdn url`, testConfig, () => {
const type = "gatsby-image-cdn"

cy.get(`[data-cy="${type}"]`)
.find(".gatsby-image-wrapper > picture > img")
.each(($el, i) => {
cy.wrap($el).should("be.visible")
cy.wrap($el)
.should("have.attr", "srcset")
.and(srcset => {
expect(srcset).to.match(/_gatsby\/image/)
cy.get(`[data-cy="${type}"] .gatsby-image-wrapper > picture > img`).then(
async $imgs => {
let i = 0
for (const $img of $imgs) {
cy.wrap($img).should("be.visible")

parseSrcset(srcset).forEach(({ url }) => {
const [, , , sourceUrl64, _args64, filename] = url.split(`/`)
const sourceUrl = window.atob(sourceUrl64)
expect(sourceUrl).to.equal(
"https://images.ctfassets.net/k8iqpp6u0ior/3BSI9CgDdAn1JchXmY5IJi/f97a2185b3395591b98008647ad6fd3c/camylla-battani-AoqgGAqrLpU-unsplash.jpg"
)
expect(filename).to.equal(
"camylla-battani-AoqgGAqrLpU-unsplash.jpg"
)
})
const res = await fetch($img.currentSrc, {
method: "HEAD",
})
expect(res.ok).to.be.true

cy.wrap($el).matchImageSnapshot(`${type}-${i}`)
})
cy.wrap($img).matchImageSnapshot(`${type}-${i++}`)
}
}
)
})
})
@@ -1,69 +1,115 @@
before(() => {
cy.exec(`npm run reset`)
})

describe(`remote-file`, () => {
before(() => {
cy.exec(`npm run reset`)
})

beforeEach(() => {
cy.visit(`/remote-file/`).waitForRouteChange()

// trigger intersection observer
cy.scrollTo("top")
cy.wait(100)
cy.scrollTo("bottom")
cy.scrollTo("bottom", {
duration: 500,
})
})

async function testImages(images, expectations) {
for (let i = 0; i < images.length; i++) {
const expectation = expectations[i]

const res = await fetch(images[i].currentSrc, {
method: "HEAD",
})
expect(res.ok).to.be.true
if (expectation.width) {
expect(Math.ceil(images[i].getBoundingClientRect().width)).to.be.equal(
expectation.width
)
}
if (expectation.height) {
expect(Math.ceil(images[i].getBoundingClientRect().height)).to.be.equal(
expectation.height
)
}
}
}

it(`should render correct dimensions`, () => {
cy.get('[data-testid="public"]').then($urls => {
cy.get('[data-testid="public"]').then(async $urls => {
const urls = Array.from($urls.map((_, $url) => $url.getAttribute("href")))

expect(urls[0].endsWith(".jpg")).to.be.true
expect(urls[1].endsWith(".jpg")).to.be.true
expect(urls[2].endsWith(".jpg")).to.be.true
for (const url of urls) {
const res = await fetch(url, {
method: "HEAD",
})
expect(res.ok).to.be.true
}
})

cy.get(".resize").then($imgs => {
const imgDimensions = $imgs.map((_, $img) => $img.getBoundingClientRect())

expect(imgDimensions[0].width).to.be.equal(100)
expect(imgDimensions[0].height).to.be.equal(133)
expect(imgDimensions[1].width).to.be.equal(100)
expect(imgDimensions[1].height).to.be.equal(160)
expect(imgDimensions[2].width).to.be.equal(100)
expect(imgDimensions[2].height).to.be.equal(67)
cy.get(".resize").then(async $imgs => {
await testImages(Array.from($imgs), [
{
width: 100,
height: 133,
},
{
width: 100,
height: 160,
},
{
width: 100,
height: 67,
},
])
})

cy.get(".fixed").then($imgs => {
const imgDimensions = $imgs.map((_, $img) => $img.getBoundingClientRect())

expect(imgDimensions[0].width).to.be.equal(100)
expect(imgDimensions[0].height).to.be.equal(133)
expect(imgDimensions[1].width).to.be.equal(100)
expect(imgDimensions[1].height).to.be.equal(160)
expect(imgDimensions[2].width).to.be.equal(100)
expect(imgDimensions[2].height).to.be.equal(67)
cy.get(".fixed").then(async $imgs => {
await testImages(Array.from($imgs), [
{
width: 100,
height: 133,
},
{
width: 100,
height: 160,
},
{
width: 100,
height: 67,
},
])
})

cy.get(".constrained").then($imgs => {
const imgDimensions = $imgs.map((_, $img) => $img.getBoundingClientRect())

expect(imgDimensions[0].width).to.be.equal(300)
expect(imgDimensions[0].height).to.be.equal(400)
expect(imgDimensions[1].width).to.be.equal(300)
expect(imgDimensions[1].height).to.be.equal(481)
expect(imgDimensions[2].width).to.be.equal(300)
expect(imgDimensions[2].height).to.be.equal(200)
cy.get(".constrained").then(async $imgs => {
await testImages(Array.from($imgs), [
{
width: 300,
height: 400,
},
{
width: 300,
height: 481,
},
{
width: 300,
height: 200,
},
])
})

cy.get(".full").then($imgs => {
const parentWidth = $imgs[0].parentElement.getBoundingClientRect().width
const imgDimensions = $imgs.map((_, $img) => $img.getBoundingClientRect())

expect(imgDimensions[0].width).to.be.equal(parentWidth)
expect(Math.ceil(imgDimensions[0].height)).to.be.equal(1229)
expect(imgDimensions[1].width).to.be.equal(parentWidth)
expect(Math.ceil(imgDimensions[1].height)).to.be.equal(1478)
expect(imgDimensions[2].width).to.be.equal(parentWidth)
expect(Math.ceil(imgDimensions[2].height)).to.be.equal(614)
cy.get(".full").then(async $imgs => {
await testImages(Array.from($imgs), [
{
height: 1229,
},
{
height: 1478,
},
{
height: 614,
},
])
})
})

Expand Down
127 changes: 86 additions & 41 deletions e2e-tests/production-runtime/cypress/integration/remote-file.js
Expand Up @@ -4,63 +4,108 @@ describe(`remote-file`, () => {

// trigger intersection observer
cy.scrollTo("top")
cy.wait(100)
cy.scrollTo("bottom", {
duration: 500,
})
})

async function testImages(images, expectations) {
for (let i = 0; i < images.length; i++) {
const expectation = expectations[i]

const res = await fetch(images[i].currentSrc, {
method: "HEAD",
})
expect(res.ok).to.be.true
if (expectation.width) {
expect(Math.ceil(images[i].getBoundingClientRect().width)).to.be.equal(
expectation.width
)
}
if (expectation.height) {
expect(Math.ceil(images[i].getBoundingClientRect().height)).to.be.equal(
expectation.height
)
}
}
}

it(`should render correct dimensions`, () => {
cy.get('[data-testid="public"]').then($urls => {
cy.get('[data-testid="public"]').then(async $urls => {
const urls = Array.from($urls.map((_, $url) => $url.getAttribute("href")))

expect(urls[0].endsWith(".jpg")).to.be.true
expect(urls[1].endsWith(".jpg")).to.be.true
expect(urls[2].endsWith(".jpg")).to.be.true
for (const url of urls) {
const res = await fetch(url, {
method: "HEAD",
})
expect(res.ok).to.be.true
}
})

cy.get(".resize").then($imgs => {
const imgDimensions = $imgs.map((_, $img) => $img.getBoundingClientRect())

expect(imgDimensions[0].width).to.be.equal(100)
expect(imgDimensions[0].height).to.be.equal(133)
expect(imgDimensions[1].width).to.be.equal(100)
expect(imgDimensions[1].height).to.be.equal(160)
expect(imgDimensions[2].width).to.be.equal(100)
expect(imgDimensions[2].height).to.be.equal(67)
cy.get(".resize").then(async $imgs => {
await testImages(Array.from($imgs), [
{
width: 100,
height: 133,
},
{
width: 100,
height: 160,
},
{
width: 100,
height: 67,
},
])
})

cy.get(".fixed").then($imgs => {
const imgDimensions = $imgs.map((_, $img) => $img.getBoundingClientRect())

expect(imgDimensions[0].width).to.be.equal(100)
expect(imgDimensions[0].height).to.be.equal(133)
expect(imgDimensions[1].width).to.be.equal(100)
expect(imgDimensions[1].height).to.be.equal(160)
expect(imgDimensions[2].width).to.be.equal(100)
expect(imgDimensions[2].height).to.be.equal(67)
cy.get(".fixed").then(async $imgs => {
await testImages(Array.from($imgs), [
{
width: 100,
height: 133,
},
{
width: 100,
height: 160,
},
{
width: 100,
height: 67,
},
])
})

cy.get(".constrained").then($imgs => {
const imgDimensions = $imgs.map((_, $img) => $img.getBoundingClientRect())

expect(imgDimensions[0].width).to.be.equal(300)
expect(imgDimensions[0].height).to.be.equal(400)
expect(imgDimensions[1].width).to.be.equal(300)
expect(imgDimensions[1].height).to.be.equal(481)
expect(imgDimensions[2].width).to.be.equal(300)
expect(imgDimensions[2].height).to.be.equal(200)
cy.get(".constrained").then(async $imgs => {
await testImages(Array.from($imgs), [
{
width: 300,
height: 400,
},
{
width: 300,
height: 481,
},
{
width: 300,
height: 200,
},
])
})

cy.get(".full").then($imgs => {
const parentWidth = $imgs[0].parentElement.getBoundingClientRect().width
const imgDimensions = $imgs.map((_, $img) => $img.getBoundingClientRect())

expect(imgDimensions[0].width).to.be.equal(parentWidth)
expect(Math.ceil(imgDimensions[0].height)).to.be.equal(1229)
expect(imgDimensions[1].width).to.be.equal(parentWidth)
expect(Math.ceil(imgDimensions[1].height)).to.be.equal(1478)
expect(imgDimensions[2].width).to.be.equal(parentWidth)
expect(Math.ceil(imgDimensions[2].height)).to.be.equal(614)
cy.get(".full").then(async $imgs => {
await testImages(Array.from($imgs), [
{
height: 1229,
},
{
height: 1478,
},
{
height: 614,
},
])
})
})

Expand Down
Expand Up @@ -5,6 +5,7 @@
const {
default: fetchGraphql,
} = require("gatsby-source-wordpress/dist/utils/fetch-graphql")
const { URL } = require("url")

const gatsbyConfig = require("../gatsby-config")

Expand Down Expand Up @@ -541,6 +542,7 @@ describe(`data resolution`, () => {
nodes {
featuredImage {
node {
filename
mediaItemUrl
resize(width: 100, height: 100, quality: 100) {
width
Expand All @@ -560,13 +562,15 @@ describe(`data resolution`, () => {
return
}

const { resize } = node.featuredImage.node
const [, , , sourceUrl64, _args64, filename] = resize.src.split(`/`)
const { resize, mediaItemUrl } = node.featuredImage.node
const parsedUrl = new URL(resize.src, "https://www.gatsbyjs.com")

const sourceUrl = Buffer.from(sourceUrl64, `base64`).toString(`ascii`)
const sourceUrl = parsedUrl.searchParams.get("u")

expect(node.featuredImage.node.mediaItemUrl).toEqual(sourceUrl)
expect(node.featuredImage.node.mediaItemUrl).toContain(filename)
expect(mediaItemUrl).toEqual(sourceUrl)
expect(
parsedUrl.pathname.endsWith(node.featuredImage.node.filename)
).toBe(true)
})
})
})