Public
Edited
Mar 7
1 star
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
zillow_data
Type Table, then Shift-Enter. Ctrl-space for more options.

Insert cell
date_extent = d3.extent([...zillow_data, ...streeteasy_data], (d) => d.date)
Insert cell
zillow_data = {
// const zillow_url = `https://files.zillowstatic.com/research/public_csvs/zori/City_zori_sm_month.csv`;
// const zillow_url = `https://files.zillowstatic.com/research/public_csvs/zori/County_zori_sm_month.csv`;
const zillow_url = `https://files.zillowstatic.com/research/public_csvs/zori/County_zori_uc_sfrcondomfr_sm_month.csv`;
const data_raw = await d3.csv(getCorsUrl(zillow_url));
const is_date = (key) => key.match(/^\d{4}-\d{2}-\d{2}/);
return data_raw
.map((row) => {
const keys = Object.keys(row);
const date_keys = keys.filter((key) => is_date(key));
const non_date_keys = keys.filter((key) => !is_date(key));
const non_date_stuff = Object.fromEntries(
non_date_keys.map((key) => [key, row[key]])
);
return date_keys.map((date_string) => ({
...non_date_stuff,
date_string,
date: new Date(date_string),
value: +row[date_string]
}));
})
.flat()
.map((d) => ({ ...d, value: d.value === 0 ? null : d.value }))
.filter((d) => d.Metro === `New York-Newark-Jersey City, NY-NJ-PA`)
.filter((d) =>
[
`New York County`,
`Kings County`,
`Queens County`,
`Bronx County`,
`Richmond County`
].includes(d.RegionName)
);
}
Insert cell
streeteasy_data = {
const full_report_url = `https://cdn-charts.streeteasy.com/Master%20Report.zip`;
const buffer = await d3.buffer(getCorsUrl(full_report_url));
console.log({ jszip });
const zip_files = await jszip.loadAsync(buffer);
const median_rent_text = await (
await jszip.loadAsync(
await zip_files.file(`medianAskingRent_All.zip`).async(`arrayBuffer`)
)
)
.file(`medianAskingRent_All.csv`)
.async(`text`);
const median_rent_raw = d3.csvParse(median_rent_text);
const median_rent_flat = median_rent_raw
.map((d) => {
const { areaName, Borough, areaType } = d;
const date_keys = Object.keys(d).filter((d) => d.match(/\d{4}-\d{2}/));
return date_keys.map((date_key) => {
return {
areaName,
Borough,
areaType,
date_key,
date: new Date(date_key),
value: +d[date_key]
};
});
})
.flat()
.map((d) => ({ ...d, value: d.value === 0 ? null : d.value }));
return median_rent_flat.filter((d) => d.areaType === `borough`);
}
Insert cell
function getCorsUrl(url) {
console.log(`Fetching CORS URL:`, url);
const corsUrl = new URL(`https://www.paulmurray.lol/api/cors`);
corsUrl.searchParams.set(`url`, url);
return corsUrl.toString();
}
Insert cell
jszip = import(`https://esm.sh/jszip`).then((mod) => mod.default)
Insert cell

Purpose-built for displays of data

Observable is your go-to platform for exploring data and creating expressive data visualizations. Use reactive JavaScript notebooks for prototyping and a collaborative canvas for visual data exploration and dashboard creation.
Learn more