<script data-pm-proxy="intercept"></script><?xml version="1.0" encoding="UTF-8"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0" xmlns:itunes="http://www.itunes.com/dtds/podcast-1.0.dtd" xmlns:googleplay="http://www.google.com/schemas/play-podcasts/1.0"><channel><title><![CDATA[Dimodelo Data Engineering]]></title><description><![CDATA[Data Warehouse/Lakehouse Architecture, Engineering and Modeling for data engineers, modelers, architects, analysts and managers.]]></description><link>https://dimodelo.substack.com</link><image><url>https://substackcdn.com/image/fetch/$s_!Ee_C!,w_256,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F051177eb-7dd5-477a-8799-237c8425c504_216x216.png</url><title>Dimodelo Data Engineering</title><link>https://dimodelo.substack.com</link></image><generator>Substack</generator><lastBuildDate>Fri, 04 Sep 2026 12:22:36 GMT</lastBuildDate><atom:link href="/__u/dimodelo.substack.com/feed" rel="self" type="application/rss+xml"/><copyright><![CDATA[Willow Box Pty Ltd ATF Willow Box Trust]]></copyright><language><![CDATA[en]]></language><webMaster><![CDATA[dimodelo@substack.com]]></webMaster><itunes:owner><itunes:email><![CDATA[dimodelo@substack.com]]></itunes:email><itunes:name><![CDATA[Adam Gilmore]]></itunes:name></itunes:owner><itunes:author><![CDATA[Adam Gilmore]]></itunes:author><googleplay:owner><![CDATA[dimodelo@substack.com]]></googleplay:owner><googleplay:email><![CDATA[dimodelo@substack.com]]></googleplay:email><googleplay:author><![CDATA[Adam Gilmore]]></googleplay:author><itunes:block><![CDATA[Yes]]></itunes:block><item><title><![CDATA[How Databricks Genie AI handled an analytics question with no context]]></title><description><![CDATA[A colleague handed a user's complex analytics request to Databricks Genie with almost no context. Here's what it got right, what it got wrong, and why. A case study in AI data analytics.]]></description><link>https://dimodelo.substack.com/p/what-happens-if-you-hand-an-analytics</link><guid isPermaLink="false">https://dimodelo.substack.com/p/what-happens-if-you-hand-an-analytics</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Wed, 02 Sep 2026 09:30:43 GMT</pubDate><enclosure url="https://substackcdn.com/image/fetch/$s_!57S0!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F355bea47-a638-4286-8458-c4ea860b8fda_1087x443.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>This article demonstrates why context and data modeling matter in the age of AI data-analytics agents. When Databricks Genie &#8220;One&#8221; was asked to respond to a user&#8217;s analytics request, it produced a well-filtered and plausible answer, but the answer was subtly wrong. The answer was wrong because the context Genie used was either unavailable, incorrect, or drawn from the wrong sources. Read on...</p><p>Recently, a colleague experimented by handing a complex user request verbatim to Databricks Genie &#8220;One&#8221; (the data consumer-facing, data-aware &#8220;AI Coworker&#8221; in Databricks). The only additional context they gave Genie One was to use the silver and gold schemas, and bronze only if really needed.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://dimodelo.substack.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Dimodelo Data Engineering is a reader-supported publication. To receive new posts and support my work, consider becoming a free or paid subscriber.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p>The request was for information on the &#8220;typical&#8221; residential urban low-voltage (LV) network. Histograms over customer counts, length, Transformer types, Conductor types, solar and battery installs, etc.</p><h2>A Primer</h2><p>To understand the analysis, you need a quick primer. An Electrical Distribution Network is divided into <strong>Feeders</strong>, long strings of connected poles and wires that originate at a Zone Substation and extend kms out into the suburbs.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!CJiS!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F244c31d9-2717-4666-8a65-c485c413db61_993x559.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!CJiS!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F244c31d9-2717-4666-8a65-c485c413db61_993x559.png 424w, /__u/substackcdn.com/image/fetch/$s_!CJiS!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F244c31d9-2717-4666-8a65-c485c413db61_993x559.png 848w, /__u/substackcdn.com/image/fetch/$s_!CJiS!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F244c31d9-2717-4666-8a65-c485c413db61_993x559.png 1272w, /__u/substackcdn.com/image/fetch/$s_!CJiS!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F244c31d9-2717-4666-8a65-c485c413db61_993x559.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!CJiS!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F244c31d9-2717-4666-8a65-c485c413db61_993x559.png" width="993" height="559" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/244c31d9-2717-4666-8a65-c485c413db61_993x559.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:559,&quot;width&quot;:993,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:44173,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/png&quot;,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:&quot;https://dimodelo.substack.com/i/213804659?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F244c31d9-2717-4666-8a65-c485c413db61_993x559.png&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="/__u/substackcdn.com/image/fetch/$s_!CJiS!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F244c31d9-2717-4666-8a65-c485c413db61_993x559.png 424w, /__u/substackcdn.com/image/fetch/$s_!CJiS!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F244c31d9-2717-4666-8a65-c485c413db61_993x559.png 848w, /__u/substackcdn.com/image/fetch/$s_!CJiS!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F244c31d9-2717-4666-8a65-c485c413db61_993x559.png 1272w, /__u/substackcdn.com/image/fetch/$s_!CJiS!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F244c31d9-2717-4666-8a65-c485c413db61_993x559.png 1456w" sizes="100vw" fetchpriority="high"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>Feeders are divided into Segments (protected by devices that isolate each segment in the event of a fault). A segment that starts at a Distribution Substation (a Site) or LV Transformer (an Asset) is an <strong>LV Segment</strong>, and it stores information such as premise count and length. </p><p>In our silver canonical asset model, we model segments like this:</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!2bPo!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F130dec28-6a3d-4860-ac0b-ec59c6cdb077_1119x466.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!2bPo!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F130dec28-6a3d-4860-ac0b-ec59c6cdb077_1119x466.png 424w, /__u/substackcdn.com/image/fetch/$s_!2bPo!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F130dec28-6a3d-4860-ac0b-ec59c6cdb077_1119x466.png 848w, /__u/substackcdn.com/image/fetch/$s_!2bPo!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F130dec28-6a3d-4860-ac0b-ec59c6cdb077_1119x466.png 1272w, /__u/substackcdn.com/image/fetch/$s_!2bPo!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F130dec28-6a3d-4860-ac0b-ec59c6cdb077_1119x466.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!2bPo!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F130dec28-6a3d-4860-ac0b-ec59c6cdb077_1119x466.png" width="1119" height="466" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/130dec28-6a3d-4860-ac0b-ec59c6cdb077_1119x466.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:466,&quot;width&quot;:1119,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:48578,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/png&quot;,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:&quot;https://dimodelo.substack.com/i/213804659?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F130dec28-6a3d-4860-ac0b-ec59c6cdb077_1119x466.png&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="/__u/substackcdn.com/image/fetch/$s_!2bPo!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F130dec28-6a3d-4860-ac0b-ec59c6cdb077_1119x466.png 424w, /__u/substackcdn.com/image/fetch/$s_!2bPo!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F130dec28-6a3d-4860-ac0b-ec59c6cdb077_1119x466.png 848w, /__u/substackcdn.com/image/fetch/$s_!2bPo!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F130dec28-6a3d-4860-ac0b-ec59c6cdb077_1119x466.png 1272w, /__u/substackcdn.com/image/fetch/$s_!2bPo!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F130dec28-6a3d-4860-ac0b-ec59c6cdb077_1119x466.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><ul><li><p><strong>Asset.</strong> All assets in the electrical network (poles, wires, transformers).</p></li><li><p><strong>Site.</strong> A location into which an asset is installed. A Distribution Substation Site contains several Assets, including an LV Transformer. Over the years, multiple transformers may be replaced at the same Distribution Site.</p></li><li><p><strong>Segment.</strong> The subset of Assets on a Feeder protected by a protection device.</p></li><li><p><strong>Segment-Asset and Segment-Site.</strong> The many-to-many relationships between a Segment and the Assets and Sites on it.</p></li><li><p><strong>protection_asset_fk.</strong> A pointer from Segment to the Asset that is the protection device for that Segment.</p></li><li><p><strong>protection_site_fk.</strong> A pointer from Segment to the Site that is the protection device for that Segment.</p></li></ul><p>Take note that there are <strong>four paths</strong> you can take to get from Segment to Asset, two of which are mutually exclusive. An LV Segment has a <code>protection_asset_fk</code> relationship if its protection device is an Asset (an LV Transformer), or a <code>protection_site_fk</code> relationship if its protection device is a Site (a Distribution Substation).</p><h2>Request 1 - Transformer Rating</h2><p>The requester asked for &#8220;transformer ratings (to identify the most common size)&#8221;. Here is the query Genie generated:</p><pre><code><code>SELECT
  asset.rating AS transformer_rating_kva,
  asset.phases,
  COUNT(*) AS count,
  ROUND(COUNT(*) * 100.0 / SUM(COUNT(*)) OVER(), 1) AS percentage
FROM slv_asset.asset AS asset
JOIN slv_asset.segment AS segment
  ON asset.site_fk = segment.protection_site_fk
WHERE segment.segment_type = 'low voltage'
  AND asset.asset_type = 'Transformer'
  AND asset.asset_status = 'Active'
  AND asset.rating IS NOT NULL
  AND segment.segment_feeder_name IN (
    SELECT df.asset_label
    FROM slv_asset.feeder df
    WHERE df.category = 'Urban'
  )
GROUP BY asset.rating, asset.phases
ORDER BY count DESC</code></code></pre><p>As you can see, Genie used tables from the silver asset canonical model to respond to this question:</p><ul><li><p><code>slv_asset.feeder</code> - Feeder classification (Urban/Rural)</p></li><li><p><code>slv_asset.segment</code> - LV segment lengths, premise counts</p></li><li><p><code>slv_asset.asset</code> - Transformer ratings, conductor materials</p></li></ul><h3>What it got right</h3><ul><li><p>The requester asked for &#8220;urban&#8221; feeders. There is a <code>category</code> column on the feeder table that was correctly used to filter by <code>category = 'Urban'</code>. Nice!</p></li><li><p>It correctly found the <code>rating</code> attribute on the asset table, filtered assets where <code>asset_type = 'Transformer'</code>, and, surprisingly, also selected only <code>'Active'</code> Transformer assets, which is desirable.</p></li><li><p>It correctly filtered to low-voltage segments only (<code>segment.segment_type = 'low voltage'</code>).</p></li><li><p>It generated a percentage, since our requestor is looking for a &#8220;typical&#8221; residential urban LV network.</p></li></ul><p>Most impressive of all, it worked out that the primary table it needed was <code>segment</code>, even though the requestor never mentioned segments. They asked about the &#8220;residential urban low voltage (LV) network,&#8221; and the AI correlated that description with low-voltage segments. We put that down to the extensive table and column descriptions we have on those tables.</p><h3>What it got wrong</h3><p><strong>It under-reported Transformers.</strong> Genie didn&#8217;t recognize that sometimes the protection device on a low-voltage Segment is an LV Transformer asset directly, via <code>protection_asset_fk</code>, rather than via its parent Distribution Substation Site. Those Transformers were excluded from the analysis. There is even a flag on Segment called <code>protection_device_is_site</code> that it could have reasoned over, but the context information for it is unclear, so perhaps that was a step too far. It was only 5% of segments, but it could easily have been 30% and produced a materially wrong number.</p><p><strong>It short-circuited the join between Segment and Asset.</strong> It reasoned that, to reach LV Transformer assets, it needed to find Distribution Substation protection Sites and then obtain the LV Transformer assets at those Sites. An analyst would join <code>segment.protection_site_fk = site.site_sk</code>, then join asset where <code>asset.site_fk = site.site_sk</code>. Genie short-circuited this and went fk to fk, bypassing Site entirely (<code>asset.site_fk = segment.protection_site_fk</code>). I can&#8217;t decide whether this is brilliant or dangerous. Same result in effect, but much harder to comprehend.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!57S0!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F355bea47-a638-4286-8458-c4ea860b8fda_1087x443.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!57S0!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F355bea47-a638-4286-8458-c4ea860b8fda_1087x443.png 424w, /__u/substackcdn.com/image/fetch/$s_!57S0!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F355bea47-a638-4286-8458-c4ea860b8fda_1087x443.png 848w, /__u/substackcdn.com/image/fetch/$s_!57S0!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F355bea47-a638-4286-8458-c4ea860b8fda_1087x443.png 1272w, /__u/substackcdn.com/image/fetch/$s_!57S0!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F355bea47-a638-4286-8458-c4ea860b8fda_1087x443.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!57S0!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F355bea47-a638-4286-8458-c4ea860b8fda_1087x443.png" width="1087" height="443" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/355bea47-a638-4286-8458-c4ea860b8fda_1087x443.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:443,&quot;width&quot;:1087,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:54219,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/png&quot;,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:&quot;https://dimodelo.substack.com/i/213804659?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F355bea47-a638-4286-8458-c4ea860b8fda_1087x443.png&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="/__u/substackcdn.com/image/fetch/$s_!57S0!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F355bea47-a638-4286-8458-c4ea860b8fda_1087x443.png 424w, /__u/substackcdn.com/image/fetch/$s_!57S0!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F355bea47-a638-4286-8458-c4ea860b8fda_1087x443.png 848w, /__u/substackcdn.com/image/fetch/$s_!57S0!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F355bea47-a638-4286-8458-c4ea860b8fda_1087x443.png 1272w, /__u/substackcdn.com/image/fetch/$s_!57S0!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F355bea47-a638-4286-8458-c4ea860b8fda_1087x443.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p></p><p><strong>It joined Segment to Feeder by name.</strong> Despite a foreign key being defined between segment and feeder, it decided to use the feeder <code>Name</code> to join. I have an issue with this one. Joins should always use foreign keys where available, and this could cause issues if the segment and feeder are not aligned on the feeder name. I had assumed we&#8217;d missed defining the foreign key relationship, but no, it is defined on the segment table. A very poor choice by the AI. More on how that might happen below.</p><p><strong>It didn&#8217;t run the query it showed us.</strong> It reported the query above, but produced two output tables, one for rating and one for phases, so it can&#8217;t have used this query exactly. There would have been two separate queries: one aggregating by rating and the other aggregating by phases only.</p><h2>Request 2 - Solar/Battery Penetration</h2><p>In this second example, the user was asking for:</p><ol><li><p>DER (Distributed energy resources) penetration</p></li><li><p>Mean number of customers with solar installed</p></li><li><p>Mean number of customers with battery systems installed</p></li></ol><p>Genie One produced this query:</p><pre><code><code>WITH urban_substations AS (
  SELECT DISTINCT sd.protection_asset_label AS substation_label
  FROM slv_asset.segment sd
  WHERE sd.segment_type = 'low voltage'
    AND sd.segment_feeder_name IN (
      SELECT df.asset_label
      FROM slv_asset.feeder df
      WHERE df.category = 'Urban'
    )
)
SELECT 
  n.substation AS substation_label,
  COUNT(DISTINCT n.NMI) AS total_customers,
  COUNT(DISTINCT CASE WHEN der.gen_type IS NOT NULL AND der.gen_type != '' THEN n.NMI END) AS solar_count,
  COUNT(DISTINCT CASE WHEN der.storage_type IS NOT NULL AND der.storage_type != '' THEN n.NMI END) AS battery_count,
  ROUND(COUNT(DISTINCT CASE WHEN der.gen_type IS NOT NULL AND der.gen_type != '' THEN n.NMI END) * 100.0 
    / NULLIF(COUNT(DISTINCT n.NMI), 0), 1) AS solar_penetration_pct,
  ROUND(COUNT(DISTINCT CASE WHEN der.storage_type IS NOT NULL AND der.storage_type != '' THEN n.NMI END) * 100.0 
    / NULLIF(COUNT(DISTINCT n.NMI), 0), 1) AS battery_penetration_pct
FROM gld_location.dim_nmi n
INNER JOIN urban_substations us 
  ON us.substation_label = n.substation
LEFT JOIN dev.gld_itg_{saas}.der_register der
  ON der.nmi = n.NMI
WHERE n.NMI_Status = 'Active'
GROUP BY n.substation
ORDER BY total_customers DESC
</code></code></pre><p>As you can see above, it used the following additional tables over Query 1:</p><ul><li><p><code>gld_itg_{saas}.der_register</code> - Solar and battery installations.</p></li><li><p><code>gld_location.dim_nmi</code> - NMI-to-substation mapping (NMI = National Metering Identifier, the unique ID for an electricity connection point)</p></li></ul><h3>What it got right</h3><ul><li><p>It discovered tables that could help it answer the question. Whether it should have used those tables is another question.</p></li><li><p>Its calculations appear correct.</p></li></ul><h3>What it got wrong</h3><ul><li><p><strong>It used an integration schema table.</strong> <code>gld_itg_{saas}.der_register</code> is a schema we created for a SaaS vendor&#8217;s integration. Its purpose is purely for integration and not analytics. Now, we did tell it to use the gold schemas, and an integration schema carries a gold prefix, so that&#8217;s partly on us. The problem is that nothing in the catalog marked that schema as unfit for analytics, while several trusted, analytics-focused gold schemas hold the same solar and battery information.</p></li><li><p><strong>It mixed production and development data.</strong> It picked the DEV version of <code>gld_itg_{saas}.der_register</code>possibly because it wasn&#8217;t deployed to production yet.</p></li><li><p><strong>It made dubious connections between tables.</strong> It joined a gold analytics dimension, <code>gld_location.dim_nmi,</code> directly to a silver table via a label, and then directly to an integration schema? A human analyst would question their choices at this point.</p></li><li><p><strong>It compensated for dubious joins by an overreliance on DISTINCT.</strong> The use of DISTINCT in an analytics query is a code smell, serving as a workaround for a modeling issue. That&#8217;s exactly what is happening here.</p></li></ul><h2>So how does Genie One choose its tables?</h2><p>To answer that, you need to understand the Genie Ontology, the automated context Genie One relies on. To quote <a href="https://www.databricks.com/blog/introducing-genie-one-genie-ontology-and-genie-agents">this Databricks article</a>: &#8220;Genie Ontology automatically extracts snippets of knowledge from tables, <strong>queries</strong>, dashboards, pipelines, and connected apps, and organizes that knowledge into a living graph of how a company works and what the data inside <em>actually</em> means.&#8221;</p><p>What troubles me here is the reliance on past <strong>queries</strong>. There&#8217;s no guarantee those queries were ever valid or effective in the first place, and I suspect this is the root cause of the questionable choices Genie made.</p><h2>Lessons and takeaways</h2><p><strong>1. It&#8217;s a good start, and an analyst&#8217;s knowledge is still extremely important.</strong> Genie did a good job discovering the right tables in the right schema, mostly, and how to filter them. An analyst could iterate over this output, with or without Genie. But it would take someone who understands the model in greater detail than the AI does and has better judgment to reach the right outcome.</p><p><strong>2. Without six person-months of prior effort, the AI had a 0% chance.</strong> All that work to shape the data into the segmentation model is what made this possible at all. The source is spread over multiple source systems, in formats and shapes incompatible with this kind of analysis. The architecture, analysis, design, modeling, and engineering work are still necessary to achieve this result.</p><p><strong>3. Modeling still matters, especially Gold dimensional modeling.</strong> There were four paths from Segment to Asset. Genie chose one, short-circuited the join, and under-reported transformers. In a dimensional model, every dimension has a direct relationship to its fact. Hence, the model has far less reasoning to do when joining data across tables, and the outcome is far more deterministic. If we had an &#8220;asset lifecycle&#8221; fact with one row per asset, directly related to the feeder, segment, site, and asset dimensions, the query would become a simple filter on <code>segment.segment_type = 'low voltage'</code>, <code>feeder.category = 'urban'</code> and <code>asset.type = 'Transformer'</code>, with metrics counted over the filtered fact.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!LRf2!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F03f630d4-5623-4134-bf7c-653a568e0417_769x445.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!LRf2!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F03f630d4-5623-4134-bf7c-653a568e0417_769x445.png 424w, /__u/substackcdn.com/image/fetch/$s_!LRf2!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F03f630d4-5623-4134-bf7c-653a568e0417_769x445.png 848w, /__u/substackcdn.com/image/fetch/$s_!LRf2!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F03f630d4-5623-4134-bf7c-653a568e0417_769x445.png 1272w, /__u/substackcdn.com/image/fetch/$s_!LRf2!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F03f630d4-5623-4134-bf7c-653a568e0417_769x445.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!LRf2!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F03f630d4-5623-4134-bf7c-653a568e0417_769x445.png" width="769" height="445" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/03f630d4-5623-4134-bf7c-653a568e0417_769x445.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:445,&quot;width&quot;:769,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:37213,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/png&quot;,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:&quot;https://dimodelo.substack.com/i/213804659?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F03f630d4-5623-4134-bf7c-653a568e0417_769x445.png&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="/__u/substackcdn.com/image/fetch/$s_!LRf2!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F03f630d4-5623-4134-bf7c-653a568e0417_769x445.png 424w, /__u/substackcdn.com/image/fetch/$s_!LRf2!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F03f630d4-5623-4134-bf7c-653a568e0417_769x445.png 848w, /__u/substackcdn.com/image/fetch/$s_!LRf2!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F03f630d4-5623-4134-bf7c-653a568e0417_769x445.png 1272w, /__u/substackcdn.com/image/fetch/$s_!LRf2!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F03f630d4-5623-4134-bf7c-653a568e0417_769x445.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p><strong>4. Context matters even more.</strong> The descriptions of columns and tables in our Unity Catalog are what enabled Genie to get even close here. It found <code>segment</code> for a request that never mentioned segments. But it also picked a DEV integration schema because nothing told it not to. Context and ontology matter more than ever, and so does context about what <em>not</em> to use.</p><p><strong>5. Past queries as context are a problem.</strong> Genie draws on query history, which captures what people did rather than what the model means, including every shortcut taken in every one-off and prototype analysis. That is my best explanation for the segment-to-feeder join by name: even though the foreign key was defined and available, the AI still favored a pattern that a human had used before.</p><p><strong>6. Over eagerness.</strong> Genie just seemed overeager, as AI does, to find a way to solve the problem. A human might pause on the issues of cross-schema joins and push back. They might search further for other solutions, or suggest a model change to answer the question properly. In other words, apply some judgment.</p><p><strong>7. I see the emergence of a new breed of Data Analytics Agents.</strong> New data analytics agents with specific jobs like fact-checkers, validators, and quality scorers that form part of an AI data analytics workflow.</p><p><strong>8. And finally, a new emphasis on modeling over reporting outcomes.</strong> Until now, Data teams have struggled to secure business buy-in to put in the necessary effort to model a data warehouse/lakehouse properly. The Businesses&#8217; emphasis on reporting and project outcomes over all else has led to poisoned models and data swamps. That status quo cannot stand in the face of data analytics AI agents and their need for context. There is now a direct correlation between data model quality and business outcomes.</p><div><hr></div><p><em>Note: We used Genie &#8220;One&#8221; for this experiment, which is a Databricks consumer-facing, data-aware &#8220;AI Coworker&#8221; in Databricks. Databricks has since introduced &#8220;Genie Agents,&#8221; where, for a given domain (max 30 tables), you can provide curated &#8220;context&#8221; for analytics. I think curated context, combined with excellent Gold-layer dimensional modeling and semantic models, will greatly enhance the success of AI reasoning for a request like this. Hmm&#8230; the next experiment. Stay tuned!</em></p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://dimodelo.substack.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Dimodelo Data Engineering is a reader-supported publication. To receive new posts and support my work, consider becoming a free or paid subscriber.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div>]]></content:encoded></item><item><title><![CDATA[Where is data analytics headed in the age of AI?]]></title><description><![CDATA[Anthropic recently published a post on self-service &#8220;Analytics&#8221; Agents. If you are wondering where Data Analytics is &#8220;going&#8221; in the age of AI, then keep reading.]]></description><link>https://dimodelo.substack.com/p/where-is-data-analytics-headed-in</link><guid isPermaLink="false">https://dimodelo.substack.com/p/where-is-data-analytics-headed-in</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Fri, 21 Aug 2026 04:43:56 GMT</pubDate><enclosure url="https://substackcdn.com/image/fetch/$s_!Ee_C!,w_256,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F051177eb-7dd5-477a-8799-237c8425c504_216x216.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>Anthropic recently published a post on self-service &#8220;Analytics&#8221; Agents. If you are wondering where Data Analytics is &#8220;going&#8221; in the age of AI, then keep reading.</p><p>An Analytics agent, given a natural language question, can reason over your Data Warehouse data model(s), generate code (SQL), and produce answers to those questions. An analytics agent is different from a coding agent. Coding is open-ended and rewarded for creativity. An analytics agent is constrained, and there is generally only one correct answer.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://dimodelo.substack.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Dimodelo Data Engineering is a reader-supported publication. To receive new posts and support my work, consider becoming a free or paid subscriber.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p>Anthropic describes their Analytics Agent solution as follows:</p><h2>The Problem</h2><p>There are three problems they encountered in their initial efforts to use an analytics agent to answer users&#8217; questions:</p><ol><li><p><strong>Which Entity?</strong> From the 1000s of entities in your data warehouse across various layers, an analytics agent could reason that it can use 10-100s of them to answer the question. Which one does it use?</p></li><li><p><strong>Agent Knowledge staleness</strong>: The agent&#8217;s knowledge of the data model failed to keep pace with evolving changes to the model; its reasoning went stale.</p></li><li><p><strong>Retrieval Failure</strong>. Even if the data model can answer the question, given the vastness of the &#8220;search space&#8221; (i.e., thousands of entities at multiple layers), does the AI agent find what it&#8217;s looking for?</p></li></ol><h2>The Solution</h2><p>Anthropic proposes (uses) the following solution, which they describe as an analytics stack:</p><ol><li><p><strong>Bottom Layer - Data Foundation</strong>: A data foundation and &#8220;single source of truth&#8221; to shrink the &#8220;search space&#8221; of plausible entities that answer any given question. The data warehouse schema, transformations, and the metadata that describes it. They specifically mention &#8220;dimensional modeling&#8221;. Data Foundation is primarily aimed at the ambiguity problem. &#8220;The fix is fewer, more heavily governed logical models: curate a small set of canonical, single source-of-truth datasets.&#8221; &#8220;The goal is that when an agent searches for a concept, it finds a single governed answer.&#8221; Treat Metadata as a first-class product and colocate it with your codebase. Coding agents work because the codebase is legible; do the same for your Analytics Agent.</p></li><li><p><strong>Source of Truth</strong>: If data foundations are the data warehouse itself, sources of truth are the reference surfaces the agent consults to navigate it. This is your semantic layer that defines metrics and further reduces ambiguity. &#8220;If a question maps cleanly to a defined metric, the agent calls a function and gets one number, the same number every other surface in the company produces.&#8221; When a matching metric is not found, lineage allows the agent to reason about which upstream model to use. They also pipe in a company knowledge graph consisting of indexed docs, roadmaps, decision logs, and organizational structure, so the agent can resolve ambient references and ask better-clarifying questions.</p></li><li><p><strong>Skills</strong>: Skills define the agent&#8217;s procedural knowledge: which datasets to consult, in what order. I.e., &#8220;try the semantic layer, but if that doesn&#8217;t work, consult these 30 reference files for this domain&#8221;. The reference files describe the tables in the domain, explicit routing triggers (if question about X, then use Y), and gotchas. These skill files live in the same repo as the code, and they use a code hook to ensure they are updated when the code changes (addressing the staleness issue). &#8220;Without skills, Claude&#8217;s ability to answer analytics questions accurately didn&#8217;t exceed 21% on our evals. Adding skills gets these numbers consistently above 95% in aggregate.&#8221;</p></li><li><p><strong>Top Layer - Validation</strong>: Anthropic discusses offline validation, in which a known answer is paired with a question, and the agent is evaluated on its ability to generate that answer given the question. They have elaborate skill validation infrastructure, even using an adversarial review skill to &#8220;aggressively challenge all underlying assumptions on a potential final answer, " which increased accuracy by 6%.&#8221;</p></li></ol><p>Interestingly, things that didn&#8217;t work:</p><ul><li><p>Using an LLM to auto-generate the semantic layer metric definitions from raw tables and query logs.</p></li><li><p>Giving the agent access to thousands of prior queries. This moved accuracy by less than a percentage point.</p></li></ul><h2>My Takeaway</h2><p>My simple takeaway is that modeling still matters, especially Dimensional and Semantic modeling, and context (metadata, data descriptions, metrics, lineage, etc.) matters even more! This is nothing new; data practitioners have been banging on about this for years. It&#8217;s just that we have had Human &#8220;agents&#8221; who can smooth over gaps and sort through ambiguity to arrive at the answers the business needs. <strong>With AI Analytics agents, that ambiguity is no longer acceptable</strong>. Data Teams need to redouble efforts in the modeling and context areas (hooray!). If your job is primarily building analytics dashboards, etc., your job may evolve to work down the stack, defining semantic models, context, and skills for AI agents to use.</p><p>I also believe that AI in the data space won&#8217;t lead to major job losses. The pent-up demand for analytics within the organization is massive and ever-evolving, and the data team currently fails to meet it.</p><p>Anthropic Article - <a href="https://claude.com/blog/how-anthropic-enables-self-service-data-analytics-with-claude">How Anthropic enables self-service data analytics with Claude | Claude by Anthropic</a></p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://dimodelo.substack.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Dimodelo Data Engineering is a reader-supported publication. To receive new posts and support my work, consider becoming a free or paid subscriber.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div>]]></content:encoded></item><item><title><![CDATA[A Data Warehouse/Lakehouse Primer]]></title><description><![CDATA[If you're interested in learning about Data Warehouse/Lakehouse architecture, design, and modeling, start here! A guided tour of my principal articles.]]></description><link>https://dimodelo.substack.com/p/a-data-warehouselakehouse-primer</link><guid isPermaLink="false">https://dimodelo.substack.com/p/a-data-warehouselakehouse-primer</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Mon, 14 Apr 2025 05:57:20 GMT</pubDate><enclosure url="https://substackcdn.com/image/fetch/$s_!Ee_C!,w_256,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F051177eb-7dd5-477a-8799-237c8425c504_216x216.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>If you read the following articles and topics in order, you will gain a good grounding in data warehouse/lakehouse architecture, design, and modelling, as well as insight into ETL patterns and project management.</p><ul><li><p><a href="/__u/dimodelo.substack.com/p/what-is-a-data-warehouse-and-why-you-need-one?r=74wjt">What is a Data Warehouse and Why do you need one?</a></p></li><li><p><a href="/__u/dimodelo.substack.com/p/data-warehouse-architecture?r=74wjt">Modern Data Warehouse Architecture</a>.</p></li><li><p>An <a href="/__u/dimodelo.substack.com/p/what-is-dimensional-modeling-introduction?r=74wjt">Introduction to Dimensional Modeling</a>, then dig further into the <a href="/__u/dimodelo.substack.com/t/star-schema">Star Schema</a> topic.</p></li><li><p>Now you are ready to understand <a href="/__u/dimodelo.substack.com/t/dimensions">Slowly Changing Dimensions</a> and Fact tables.</p></li><li><p>A <a href="/__u/dimodelo.substack.com/p/what-is-a-semantic-layer-what-why-how-and-more?r=74wjt">Semantic Layer</a> is essential to your overall architecture. </p></li><li><p>Last but certainly not least are the <a href="/__u/dimodelo.substack.com/t/etl">ETL</a> and <a href="/__u/dimodelo.substack.com/t/staging">Staging</a> topics.</p></li></ul><p>And as a bonus:</p><ul><li><p>Some articles on <a href="/__u/dimodelo.substack.com/t/data-warehouse-project">Project approach, method and management</a>. </p></li></ul><p></p><p></p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://dimodelo.substack.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Dimodelo Data Engineering is a reader-supported publication. To receive new posts and support my work, consider becoming a free or paid subscriber.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div>]]></content:encoded></item><item><title><![CDATA[To hash or not to hash (dimension surrogate keys) ... that is the question?]]></title><description><![CDATA[This article explores why hash surrogate keys should be avoided in a data warehouse and makes the case for sticking with integer surrogate keys.]]></description><link>https://dimodelo.substack.com/p/avoid-hash-surrogate-keys-in-data-warehouse-dimensions</link><guid isPermaLink="false">https://dimodelo.substack.com/p/avoid-hash-surrogate-keys-in-data-warehouse-dimensions</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Thu, 30 Jan 2025 05:49:48 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/e42b7bcf-4a05-48e6-8bf9-146507ff5472_1536x1024.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<h2>Background</h2><p>Traditionally, the Kimball methodology for data warehousing has advocated using integer surrogate keys to uniquely identify dimension records. This approach has been widely adopted due to its storage, indexing, and query performance efficiency. However, with the advent of Data Vault modeling, the use of hash keys as surrogate identifiers became popular.</p><p>The rationale behind hash keys in Data Vault is that they provide deterministic identifiers that can be generated on the fly based on business keys, eliminating the need for lookups when inserting records. This concept has since influenced broader data warehouse architecture, leading some to use hash keys as surrogate keys in traditional dimension tables.</p><p>However, using hash keys in dimensional models introduces significant drawbacks that outweigh any perceived benefits. This article explores why hash surrogate keys should be avoided in a data warehouse and makes the case for sticking with integer surrogate keys.</p><div><hr></div><h2>The Case AGAINST Hash Surrogate Keys in a Data Warehouse</h2><h3>1. Hash Keys Do Not Eliminate Lookups for Type 2 Dimensions</h3><p>One of the primary arguments for using hash keys is that they allow fact tables to reference dimension records without requiring lookups during fact table loads. However, this is only true if all dimension attributes are Type 1 (i.e., they do not track historical changes).</p><p>In reality, many dimensions contain Type 2 attributes. This means a lookup is required during a Fact load to find the correct historical version of a dimension member before assigning a foreign key in the fact table. Since lookups are still necessary for Type 2 dimensions, the supposed efficiency gain of using hash keys is diminished in practical data warehouse implementations.</p><h3>2. Hash Keys Are Larger and Increase Storage and I/O Overhead</h3><p>A key consideration in any data warehouse design is the size of foreign keys in fact tables. Fact tables tend to have many rows and are frequently accessed. The standard integer data type in most relational databases is 4 bytes, whereas a SHA-1 hash key is 20 bytes. SHA-2 can be even larger, depending on the bit length used (e.g., SHA-256 is 32 bytes, and SHA-512 is 64 bytes).</p><p>This difference in key size has serious implications:</p><ul><li><p>Fact tables with many foreign keys experience <strong>significant storage bloat</strong> when using hash keys.</p></li><li><p>Increased I/O due to larger row sizes results in <strong>slower query performance</strong>.</p></li><li><p>Indexes and joins become less efficient because hash keys are more complex to compare than integers.</p></li></ul><h3>3. Hash Keys Reduce Query Performance</h3><p>Indexes are crucial in optimizing query performance, and integer-based indexes perform significantly better than hash-based indexes. Hash values are inherently more random and do not cluster well in typical B-tree indexes used by relational databases. As a result, joins between fact and dimension tables using hash keys are often slower than joins using integer surrogate keys.</p><p>PostgreSQL users, for example, have noted this issue in practice, as discussed in <a href="https://stackoverflow.com/questions/1638577/storing-sha1-signature-as-primary-key-in-postgres-sql">this Stack Overflow post</a>.</p><h3>4. Increased Computational Overhead</h3><p>Using hash keys requires additional computation at multiple stages of the ETL process:</p><ul><li><p>When inserting a new dimension record, the hash must be generated.</p></li><li><p>When inserting a fact record, the hash must be recalculated to determine the correct dimension reference.</p></li></ul><p>This added processing burden can slow ETL jobs, especially for large data loads. In contrast, integer surrogate keys are simple, auto-incrementing values that require no computation.</p><div><hr></div><h2>The Case FOR Integer Surrogate Keys</h2><p>Given the drawbacks of hash keys, integer surrogate keys remain the best practice for data warehouse dimensions. Here&#8217;s why:</p><h3>1. Reduced Fact Table Storage and I/O</h3><p>Fact tables often contain millions or even billions of rows. Using 4-byte integers instead of 20+ byte hash keys reduces storage requirements and improves query performance by minimizing I/O. If the number of unique dimension records is expected (very unlikely) to exceed the 4.2 billion limit of a standard <code>int</code>, then a <code>bigint</code> (8 bytes) can be used, which still offers significantly better performance than hash keys.</p><h3>2. Better Performance in Joins and Queries</h3><p>Integer surrogate keys are optimized for B-tree indexing, leading to faster joins between fact and dimension tables. Since relational databases are designed to efficiently manage integer-based primary keys, using them ensures better query execution plans and overall system performance.</p><h3>3. Flexibility with Different Integer Data Types</h3><p>Integer-based surrogate keys offer flexibility in choosing the optimal data type:</p><ul><li><p><code>tinyint</code> (1 byte): Stores up to 255 values.</p></li><li><p><code>smallint</code> (2 bytes): Stores up to 32,767 values.</p></li><li><p><code>int</code> (4 bytes): Stores up to 4.2 billion values.</p></li><li><p><code>bigint</code> (8 bytes): Stores up to 9 quintillion values.</p></li></ul><p>Using the smallest practical integer type minimizes storage requirements while maintaining efficient join performance. Moreover, different integer types can be joined without conversion in most relational databases, so mixing <code>smallint</code>, <code>int</code>, and <code>bigint</code> across tables does not create significant performance issues.</p><div><hr></div><h2>The Evidence!</h2><p>Recently, a colleague of mine built an example Fact table with just three Dimensions. He built two versions, one with bigint surrogate keys and the other with hash SHA2 512 surrogate keys. This test would have been better with integer instead of bigint and SHA1, but this is still representative of the results. </p><ul><li><p>Fact table - 673M rows</p></li><li><p>Asset Dimension 10M rows</p></li><li><p>Rate Type Dimension 3 rows</p></li><li><p>Failure Dimension 4 rows</p></li></ul><p>Here are the results:</p><div id="datawrapper-iframe" class="datawrapper-wrap outer" data-attrs="{&quot;url&quot;:&quot;https://datawrapper.dwcdn.net/Aydme/1/&quot;,&quot;thumbnail_url&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/a1ec52e4-3d15-4fd1-9f88-e63857df0ccb_1260x660.png&quot;,&quot;thumbnail_url_full&quot;:&quot;&quot;,&quot;height&quot;:334,&quot;title&quot;:&quot;Table Size&quot;,&quot;description&quot;:&quot;&quot;,&quot;belowTheFold&quot;:true}" data-component-name="DatawrapperToDOM"><iframe id="iframe-datawrapper" class="datawrapper-iframe" src="https://datawrapper.dwcdn.net/Aydme/1/" width="730" height="334" frameborder="0" scrolling="no" loading="lazy"></iframe><script type="text/javascript">!function(){"use strict";window.addEventListener("message",(function(e){if(void 0!==e.data["datawrapper-height"]){var t=document.querySelectorAll("iframe");for(var a in e.data["datawrapper-height"])for(var r=0;r<t.length;r++){if(t[r].contentWindow===e.source)t[r].style.height=e.data["datawrapper-height"][a]+"px"}}}))}();</script></div><p>The Fact Table Integer version was 1/3 the size. The Fact table will gain the most advantage because it has multiple Dimension foreign keys. </p><div><hr></div><div id="datawrapper-iframe" class="datawrapper-wrap outer" data-attrs="{&quot;url&quot;:&quot;https://datawrapper.dwcdn.net/vmYWM/1/&quot;,&quot;thumbnail_url&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/8ec659a3-dcfa-42f3-bbe1-804946590905_1260x660.png&quot;,&quot;thumbnail_url_full&quot;:&quot;&quot;,&quot;height&quot;:192,&quot;title&quot;:&quot;Fact table Load Time&quot;,&quot;description&quot;:&quot;&quot;,&quot;belowTheFold&quot;:true}" data-component-name="DatawrapperToDOM"><iframe id="iframe-datawrapper" class="datawrapper-iframe" src="https://datawrapper.dwcdn.net/vmYWM/1/" width="730" height="192" frameborder="0" scrolling="no" loading="lazy"></iframe><script type="text/javascript">!function(){"use strict";window.addEventListener("message",(function(e){if(void 0!==e.data["datawrapper-height"]){var t=document.querySelectorAll("iframe");for(var a in e.data["datawrapper-height"])for(var r=0;r<t.length;r++){if(t[r].contentWindow===e.source)t[r].style.height=e.data["datawrapper-height"][a]+"px"}}}))}();</script></div><p>The Integer version was 42% faster.</p><div><hr></div><div id="datawrapper-iframe" class="datawrapper-wrap outer" data-attrs="{&quot;url&quot;:&quot;https://datawrapper.dwcdn.net/Sv3y3/1/&quot;,&quot;thumbnail_url&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/81f1b45c-263a-4379-9c01-5141a5387289_1260x660.png&quot;,&quot;thumbnail_url_full&quot;:&quot;&quot;,&quot;height&quot;:204,&quot;title&quot;:&quot;Query Performance (less is better)&quot;,&quot;description&quot;:&quot;&quot;,&quot;belowTheFold&quot;:true}" data-component-name="DatawrapperToDOM"><iframe id="iframe-datawrapper" class="datawrapper-iframe" src="https://datawrapper.dwcdn.net/Sv3y3/1/" width="730" height="204" frameborder="0" scrolling="no" loading="lazy"></iframe><script type="text/javascript">!function(){"use strict";window.addEventListener("message",(function(e){if(void 0!==e.data["datawrapper-height"]){var t=document.querySelectorAll("iframe");for(var a in e.data["datawrapper-height"])for(var r=0;r<t.length;r++){if(t[r].contentWindow===e.source)t[r].style.height=e.data["datawrapper-height"][a]+"px"}}}))}();</script></div><p>The query performance of the integer version was up to 4 times faster.</p><div><hr></div><h2>Addressing Fact Table Lookups for Dimensions</h2><p>One concern raised against integer surrogate keys is the need for lookups when inserting fact records. However, this is only necessary for Type 2 dimensions. For dimensions that are guaranteed to contain only Type 1 attributes, the need for lookups can be eliminated through strategic design choices. Follow this decision tree to determine what type of surrogate key to use. </p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!T56m!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffa4035e5-34c5-4381-bcaf-d36119433249_297x623.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!T56m!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffa4035e5-34c5-4381-bcaf-d36119433249_297x623.png 424w, /__u/substackcdn.com/image/fetch/$s_!T56m!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffa4035e5-34c5-4381-bcaf-d36119433249_297x623.png 848w, /__u/substackcdn.com/image/fetch/$s_!T56m!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffa4035e5-34c5-4381-bcaf-d36119433249_297x623.png 1272w, /__u/substackcdn.com/image/fetch/$s_!T56m!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffa4035e5-34c5-4381-bcaf-d36119433249_297x623.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!T56m!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffa4035e5-34c5-4381-bcaf-d36119433249_297x623.png" width="297" height="623" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/fa4035e5-34c5-4381-bcaf-d36119433249_297x623.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:623,&quot;width&quot;:297,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:23559,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/png&quot;,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:&quot;https://dimodelo.substack.com/i/160235374?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffa4035e5-34c5-4381-bcaf-d36119433249_297x623.png&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="/__u/substackcdn.com/image/fetch/$s_!T56m!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffa4035e5-34c5-4381-bcaf-d36119433249_297x623.png 424w, /__u/substackcdn.com/image/fetch/$s_!T56m!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffa4035e5-34c5-4381-bcaf-d36119433249_297x623.png 848w, /__u/substackcdn.com/image/fetch/$s_!T56m!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffa4035e5-34c5-4381-bcaf-d36119433249_297x623.png 1272w, /__u/substackcdn.com/image/fetch/$s_!T56m!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffa4035e5-34c5-4381-bcaf-d36119433249_297x623.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>Although this method does introduce some variability and, therefore, complexity, it is well worth the time it saves in ETL load processes. I recommend a comment on each Dimension&#8217;s surrogate key explaining how the surrogate key is formed.</p><h3>1. Using Smart Keys</h3><p>Certain dimensions, such as the Date dimension, can use a <strong>smart key</strong> that encodes meaningful information. For example, a date key might be stored as an integer in <code>YYYYMMDD</code> format (e.g., <code>20250124</code>). This eliminates the need for a lookup while keeping keys small and efficient.</p><h3>2. Integer Natural Keys</h3><p>If a dimension&#8217;s primary key is an integer and never requires Type 2 changes, it can be used directly as the foreign key in the fact table. Should the need for Type 2 tracking arise later, a new surrogate key system can be implemented while preserving historical data integrity. For example, the surrogate key can be set using a formula like max(surrogate_key) + row_num.</p><h3>3. Character-Based Natural Keys (When Justified)</h3><p>Although Kimball generally recommends against using character natural keys, there are cases where it can make sense&#8212;particularly if the key is short and unique (e.g., product codes, state abbreviations). A prefix, such as <code>K-</code>, can be used to distinguish keys from other attributes. If composite keys are required and their combined length exceeds 20 bytes, a hash may be justified, but this should be an exception rather than the norm.</p><div><hr></div><h2>Conclusion</h2><p>While hash surrogate keys have a place in Data Vault modeling, they are <strong>not well-suited for traditional data warehouse dimension tables</strong>. The disadvantages&#8212;larger storage requirements, poorer indexing performance, increased computational overhead, and slower queries&#8212;far outweigh any perceived benefits.</p><p>For best performance and scalability in a dimensional model, integer surrogate keys remain the superior choice. Fact tables benefit from reduced storage and I/O, joins are optimized, and overall query performance improves. By thoughtfully designing dimension keys and employing lookup strategies only where necessary, you can build a highly efficient and maintainable data warehouse.</p><h3>Key Takeaways:</h3><ul><li><p>Use integer surrogate keys whenever possible. </p></li><li><p>Select the smallest practical integer type to minimize storage. </p></li><li><p>Use smart keys for dimensions like Date where feasible. </p></li><li><p>Consider integer natural keys if Type 2 changes will never be needed. </p></li><li><p>Avoid hash keys unless dealing with exceptionally long composite natural keys.</p></li></ul><p>By following these principles, your data warehouse will remain performant, scalable, and easy to manage.</p>]]></content:encoded></item><item><title><![CDATA[Data Warehouse Architecture]]></title><description><![CDATA[The modern Data Warehouse architecture has evolved to meet the growing demands of big data and data science, leveraging new technologies to do so. It selectively integrates the most effective elements]]></description><link>https://dimodelo.substack.com/p/data-warehouse-architecture</link><guid isPermaLink="false">https://dimodelo.substack.com/p/data-warehouse-architecture</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Thu, 15 Aug 2024 07:19:48 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/174bc442-2cab-4682-ad3d-6b4bd7cf4cb6_1040x568.webp" length="0" type="image/jpeg"/><content:encoded><![CDATA[<h2>What is Data Warehouse Architecture</h2><p>Before you build a <a href="/__u/dimodelo.substack.com/p/what-is-a-data-warehouse-and-why-you-need-one/">data warehouse</a>, you must define some standards for how you and your team will design and structure your data warehouse system. A Data Warehouse Architecture describes how data is sourced, stored, processed, and accessed. The architecture can vary depending on the specific needs and scale of the organization, but generally, it will follow a layered approach.</p><p>There have been various Data Warehouse Architecture articulated by well-known experts in the field. These architectures have included:</p><ul><li><p>Kimball Dimensional Data Warehouse Architecture</p></li><li><p>Inmon Data Warehouse Architecture</p></li><li><p>Data Lakehouse Architecture</p></li><li><p>Data Vault Architecture</p></li></ul><p>What all these architectures have in common is they are layered, include a dimensional presentation layer and exhibit the characteristics outlined below:</p><ol><li><p><strong>Integrated</strong>. A data warehouse takes a copy of the data (on a regular basis) from the enterprise&#8217;s application systems. It integrates that data into &#8220;one place&#8221;, simplifying data access for reporting purposes. A second form of integration is to match and merge data from multiple systems into single subject-oriented entities.</p></li><li><p><strong>Subject-oriented, not source system-oriented</strong>. A data warehouse reorganises the source data into business subjects/domains, making it easier for users to understand and consume.</p></li><li><p><strong>Historical/Time Variant</strong>. A Data Warehouse records the history of how data changes. This is important for accurate reporting, auditing and efficient data management.</p></li><li><p><strong>Non-Volatile</strong>. Data is loaded in periodic &#8220;batches&#8221;. The data doesn&#8217;t change from moment to moment; rather, it&#8217;s stable between load periods. This means reporting and analysis can be conducted without the data changing underneath you.</p></li></ol><p>Here, you will discover the latest thinking in modern data warehouse design. It represents a blend of previous architectures, selectively incorporating the best elements from established designs.</p><h2>Modern Data Warehouse Architecture</h2><p>The modern Data Warehouse architecture has evolved to meet the growing demands of big data and data science, leveraging new technologies to do so. It selectively integrates the most effective elements of traditional architectures, resulting in a mature, comprehensive platform that can address a wide range of use cases. The key factors driving this evolution include:</p><ul><li><p>New &#8220;big data&#8221; technologies like Hadoop and Spark (e.g. Databricks).</p></li><li><p>A desire to unify data warehousing and business intelligence with new requirements like machine learning, data science, and reverse ETL.</p></li><li><p>The advent of Cloud data platforms (like Databricks, Snowflake and Fabric).</p></li><li><p>Many years of experience of leading practitioners.</p></li></ul><p>The modern data warehouse architecture consists of 6 Layers, including the Visualization layer. The diagram below summarizes each layer and its purpose and contrasts it with the Data Lakehouse architecture.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!k-uy!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F926c3958-83fd-4654-8d71-6ea28c5706b9_1040x568.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!k-uy!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F926c3958-83fd-4654-8d71-6ea28c5706b9_1040x568.webp 424w, /__u/substackcdn.com/image/fetch/$s_!k-uy!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F926c3958-83fd-4654-8d71-6ea28c5706b9_1040x568.webp 848w, /__u/substackcdn.com/image/fetch/$s_!k-uy!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F926c3958-83fd-4654-8d71-6ea28c5706b9_1040x568.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!k-uy!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F926c3958-83fd-4654-8d71-6ea28c5706b9_1040x568.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!k-uy!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F926c3958-83fd-4654-8d71-6ea28c5706b9_1040x568.webp" width="1040" height="568" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/926c3958-83fd-4654-8d71-6ea28c5706b9_1040x568.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:568,&quot;width&quot;:1040,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;Modern data warehouse architecture layers&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="Modern data warehouse architecture layers" title="Modern data warehouse architecture layers" srcset="/__u/substackcdn.com/image/fetch/$s_!k-uy!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F926c3958-83fd-4654-8d71-6ea28c5706b9_1040x568.webp 424w, /__u/substackcdn.com/image/fetch/$s_!k-uy!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F926c3958-83fd-4654-8d71-6ea28c5706b9_1040x568.webp 848w, /__u/substackcdn.com/image/fetch/$s_!k-uy!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F926c3958-83fd-4654-8d71-6ea28c5706b9_1040x568.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!k-uy!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F926c3958-83fd-4654-8d71-6ea28c5706b9_1040x568.webp 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">modern data warehouse architecture layers</figcaption></figure></div><p>This may seem unnecessarily complex, but the layered approach simplifies the architecture technically and conceptually, with each layer serving its role and purpose. The design principles behind this layered approach are well-known software engineering principles that have matured as software design and delivery have matured. They include:</p><ul><li><p><strong>DRY (Don&#8217;t Repeat Yourself)</strong>: Avoid redundancy by ensuring that every piece of logic is represented only once in the codebase.</p></li><li><p><strong>Separation of Concerns</strong>: Divide into components, each addressing a separate &#8220;concern&#8221; or doing a different &#8220;job&#8221; to simplify manageability and maintainability. The layered approach is an example of the separation of concerns.</p></li><li><p><strong>Patterns</strong>: Data engineers who work with data warehouses or lakehouses for an extended period will begin to identify recurring code patterns. They often repeat the same code over and over for multiple entities. Adopting a layered approach with a &#8220;separation of concerns&#8221; can help isolate these patterns, allowing for standardization and, eventually, automation.</p></li><li><p><strong>Portability</strong>: Data platforms change over time, and new platforms are arising at an ever-increasing pace. You don&#8217;t want to be locked into any one vendor. At Dimodelo, we emphasize defining architectures and patterns that can be implemented with any data platform, ETL tool, or transformation language. The tools can change, but the architecture, standards, and patterns remain the same.</p></li></ul><p>A key aspect of the modern data warehouse is how data flows through each layer. The process of &#8220;moving&#8221; the data is known as ETL, an acronym for Extract, Transform and Load. The diagram below is an overview of the various processes that occur to load each of the layers. The layered approach allows for the separation of concerns at each layer. This, in turn, allows us to identify, implement and even automate common patterns and standards at each layer.</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!2k3K!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F289d7d79-eebf-4b46-bb97-1a7950c1473d_555x890.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!2k3K!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F289d7d79-eebf-4b46-bb97-1a7950c1473d_555x890.webp 424w, /__u/substackcdn.com/image/fetch/$s_!2k3K!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F289d7d79-eebf-4b46-bb97-1a7950c1473d_555x890.webp 848w, /__u/substackcdn.com/image/fetch/$s_!2k3K!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F289d7d79-eebf-4b46-bb97-1a7950c1473d_555x890.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!2k3K!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F289d7d79-eebf-4b46-bb97-1a7950c1473d_555x890.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!2k3K!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F289d7d79-eebf-4b46-bb97-1a7950c1473d_555x890.webp" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/289d7d79-eebf-4b46-bb97-1a7950c1473d_555x890.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:null,&quot;width&quot;:null,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;modern data warehouse architecture dimodelo.com&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="modern data warehouse architecture dimodelo.com" title="modern data warehouse architecture dimodelo.com" srcset="/__u/substackcdn.com/image/fetch/$s_!2k3K!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F289d7d79-eebf-4b46-bb97-1a7950c1473d_555x890.webp 424w, /__u/substackcdn.com/image/fetch/$s_!2k3K!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F289d7d79-eebf-4b46-bb97-1a7950c1473d_555x890.webp 848w, /__u/substackcdn.com/image/fetch/$s_!2k3K!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F289d7d79-eebf-4b46-bb97-1a7950c1473d_555x890.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!2k3K!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F289d7d79-eebf-4b46-bb97-1a7950c1473d_555x890.webp 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a><figcaption class="image-caption">Modern Data Warehouse Architecture</figcaption></figure></div><p>You&#8217;ll notice that the modern data warehouse architecture shows a relationship to Data Science/Machine Learning and Data Integration/Reverse ETL. I address these aspects in the &#8220;<a href="#extending-data-warehouse-architecture">Extending the Data Warehouse Architecture</a>&#8221; Section.</p><h2>Layers of the Data Warehouse Architecture</h2><h3>Landing Layer</h3><p>The sole function of the landing layer is to &#8220;land&#8221; or store the data retrieved from source systems, which is ready for further processing. In today&#8217;s world, this data can be in various formats, such as structured (tabular), semi-structured (e.g., XML, JSON), and unstructured (e.g., emails, documents). The Landing layer must be capable of capturing all of it. The Landing layer is the equivalent of the underlying data lake of a Data Lakehouse medallion architecture.</p><p>Typically, the Landing layer is implemented as a file system (such as HDFS or Data Lake) where an ETL Extraction tool deposits files representing data extracted from source systems. The ETL tool will read structured or semi-structured data in its raw format and write it in a standardised format (e.g., parquet, proprietary, CSV, etc.). This standardised format helps standardize and automate the downstream Staging layer ETL patterns.</p><p>The Landing layer data can be transient. That is, once a Persistent Staging Layer has captured the data, the data can be deleted. However, in some cases, especially for unstructured data, there may be good reason to keep the data in the Landing layer, typically for machine learning or data science purposes.</p><p>Landing layers are often loaded with dedicated Extraction tools like Airbyte, Fivetran or Qlik. These tools specialize in connecting to source systems, extracting data incrementally where possible, and landing it in the Landing layer. They typically excel at this job but don&#8217;t work well (if at all) at transforming the data.</p><p>The data schema in the Landing layer model will match the source systems schema.</p><p>Typically, the landing layer is only accessible to data engineers responsible for creating and maintaining it. The exception may be data scientists working with unstructured data.</p><p>Extract patterns tend to fall into one of the below:</p><ul><li><p><strong>Full Extract</strong>. All the data in the source entity is extracted.</p></li><li><p><strong>Incremental Extract</strong>. Only the changed data is extracted from the source. This method is much faster than a Full extract. However, the source entity must support it. For the pattern to work, you need to identify a column or multiple columns that the source system uses to track change. They would usually be a modified date or sequential identifier. The downside of this pattern is that it doesn&#8217;t detect hard row deletes from the source. That makes it necessary to run a period Full Extract as well.</p></li><li><p><strong>Change Tracking</strong>. The change tracking pattern uses the change tracking mechanism of the source system(e.g., change tracking in Microsoft SQL Server) to identify changes in the source entity and extract only changed data. The Change Tracking pattern has an advantage over the Incremental pattern in that it recognizes hard deletes and is, therefore, a superior pattern if available.</p></li><li><p><strong>File Pattern</strong>. Extracting files is quite simple&#8212;it&#8217;s effectively a copy-and-paste. However, files can be very unreliable and variable in nature. There may be many files in the source that represent a single entity. The files might represent Full, Incremental, Change tracking or Date Range extracts. Files are probably the most unreliable with respect to their schema stability. From an extract perspective, file sources are reasonably simple but quite complex from an ingestion standpoint.</p></li><li><p><strong>Date Range Pattern</strong>.&nbsp;The date range pattern is used to extract a subset of the source data based on a date range. The end of the date range is the &#8220;current&#8221; date, and the start range is the number of days before the current date. The date range &#8216;window&#8217; moves forward a day as the current batch effective date changes. For example, you might have a very large transaction table that doesn&#8217;t support either incremental or change tracking. Instead of doing a Full extract every day, you might only extract the last 31 days of transaction data each day to capture any changes that have occurred in the last month.</p></li></ul><h3>(Persistent) Staging Layer</h3><p>Traditionally, the Staging layer served as a temporary area where raw data was collected, cleaned, and prepared before being transformed and loaded into the Presentation layer. In the modern data warehouse architecture, the Landing layer now assumes the role of data &#8220;collection&#8221;, while the Staging layer has evolved into a &#8220;persistent&#8221; Staging layer that permanently records the source data and its change history.</p><p>The Staging layer is the equivalent of the Bronze layer of the Data Lakehouse medallion architecture.</p><p>The Persistent Staging layer serves as a reliable foundation of the data warehouse. If all else fails (literally), the higher data warehouse layers can be rebuilt from this foundation. Indeed, as long as the Persistent Staging layer stays consistent, you can confidently change, modify and reload higher layers with full history without losing data. This wasn&#8217;t possible with older data architectures where the Presentation layer was the first persistent layer in the architecture. The concept of a Persistent Staging layer evolved because of problems with reloading and changing the Presentation layer, which resulted in historical data loss.</p><p>The schema of persistent staging data is tabular based, in either a database table format or file-based formats that lend themselves to tabular formats, such as Parquet with Delta table or Apache Iceberg.</p><p>The schema of the persistent staging layer closely mirrors the source system schema, except for some additional data management columns used for handling history and ETL processes. While the format might change, such as converting from JSON to tabular, resulting in some flattening, the column names and structure remain the same. There should be no data transformation.</p><p>Modern data platforms like Databricks, Snowflake, and Microsoft Fabric can directly read files from a Landing layer. The code required to write data and maintain history in a target persistent staging table can be implemented on your preferred data platform.</p><p>Typically, the ingestion pattern for Persistent Staging entities can be standardised.</p><ul><li><p>Identify the delta change data set, I.e., only the data that has changed since the last execution. This depends on the extract pattern used to extract the data from the source. Identifying the delta change set is easy for Incremental and Change Tracking patterns. A full comparison with the target persistent staging entity is required for Full extracts. A full comparison with the target Persistent Staging entity over the date range is required for date range extracts. For file extracts, it&#8217;s dependent on the pattern the file represents.</p></li><li><p>Once identified, the delta change set can be applied to the target persistent staging entity in a straightforward and standardized way.</p></li></ul><h3>Modelled Layer</h3><p>The &#8220;modelled&#8221; layer is also known as the &#8220;Core&#8221; or &#8220;Middle&#8221; or &#8220;Reconciled&#8221; or &#8220;Transformed&#8221; layer. We chose the word &#8220;Modelled&#8221; because it seems the most descriptive to us.</p><p>The<strong> Modelled layer</strong> marks the beginning of the data&#8217;s transition into a subject-oriented format. This layer is where the complex process of transformation takes place. Here, data from various systems is commonly consolidated and transformed into entities within a subject area. Data from multiple systems is matched and integrated to form a whole-of-enterprise view of key data entities. It serves as the central enterprise business model on which all enterprise reporting is built, not directly but as the foundation. The Modelled layer is the equivalent of the Silver layer in the Data Lakehouse medallion architecture.</p><p>The important thing is that the data model is subject-oriented. &#8220;Subject-oriented&#8221; refers to the organization of data around the key subjects and entities of the enterprise rather than around the source system representation (schema) of entities. Data is grouped by major subjects with entities relevant to that subject area, such as customers, products, sales, or orders. Each subject area is designed to provide a comprehensive view of the data related to that area.</p><p>Subject-oriented data modelling ensures that sometimes complex business logic is captured in one place, adhering to the DRY principle. This makes data consistent and standardized across the enterprise, reducing redundancy and discrepancies. Organizing data around subject areas fosters a common understanding across the enterprise and makes accessing data related to specific areas of interest easier for developers.</p><p>Remodelling your data from the source schema to your own subject area model decouples higher layers (i.e., presentation, semantic, and reporting) from source systems. If a source system is replaced (as it often is), it just requires &#8220;plugging in&#8221; the new source system to the existing Modelled layer schema. No reports, presentation, or semantic layer code must change (in theory).</p><p>The Modelled layer data model can take a few forms. Different teams and data architects have their preferences. The options include:</p><ul><li><p><strong>3rd Normal Form</strong>. 3rd normal form is highly normalized data usually used in the database of operational systems. It&#8217;s often overkill for the Modelled layer of a data warehouse, but it does provide norms and structures for developers to follow. Bill Inmon&#8217;s corporate information factory is an example of this approach.</p></li><li><p><strong>Data Vault</strong>. A Data Vault is designed for the modelled layer of a data warehouse. However, practitioners often find it difficult to understand and apply consistently. The <a href="https://www.ben-morris.com/data-vault-2-modelling-the-good-the-bad-and-the-downright-confusing/">criticism of data vault</a> is its &#8220;explanation tax&#8221; where you &#8220;spend a lot of time explaining the nuances to stakeholders, both technical and non-technical&#8221;. I personally am not a fan. It&#8217;s a lot of work for little return.</p></li><li><p><strong>Pragmatic</strong>. A pragmatic approach simply treats the Modelled layer as a stepping stone to the presentation layer. It doesn&#8217;t follow any particular rule set or modelling technique. It&#8217;s usually highly denormalized. It can work for smaller teams where the primary outcome is business intelligence, reporting, and analytics. It requires the least effort but can become unruly after some time.</p></li><li><p><strong>Hybrid</strong>. A hybrid approach is a cross between the 3rd Normal Form and the Pragmatic. It still identifies key subject-oriented entities and their relationships but is pragmatic in allowing denormalization to support the presentation layer.</p></li></ul><p>At Dimodelo, we favour a hybrid approach. The modelled layer must trade off effort and utility. We favour a third Normal Form schema, with denormalized tables wherever possible. Modelling is an art, not a science, so it&#8217;s difficult to define an exact description of how this is achieved. In later posts, I&#8217;ll develop some examples.</p><p>Modern data platforms such as Databricks, Snowflake, and Microsoft Fabric provide procedural languages like SQL and Python that you can use to implement the entities in the Modelled layer.</p><h3>Presentation Layer</h3><p>The<strong> </strong>presentation layer is the final subject-oriented representation of the data designed specifically to support business intelligence use cases such as reporting, ad hoc analysis, and dashboards. It is modelled using a strict Star Schema, which is comprised of Dimensions and Facts and their relationships. Data in the Modelled layer is read and transformed into the Dimensions and Facts of the Star Schema. The Presentation layer is the equivalent of the Gold Layer in the Data Lakehouse medallion architecture.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!1mUI!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feeaaf67b-b39b-4fd6-aefc-7e0f2e142c5d_680x532.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!1mUI!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feeaaf67b-b39b-4fd6-aefc-7e0f2e142c5d_680x532.webp 424w, /__u/substackcdn.com/image/fetch/$s_!1mUI!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feeaaf67b-b39b-4fd6-aefc-7e0f2e142c5d_680x532.webp 848w, /__u/substackcdn.com/image/fetch/$s_!1mUI!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feeaaf67b-b39b-4fd6-aefc-7e0f2e142c5d_680x532.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!1mUI!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feeaaf67b-b39b-4fd6-aefc-7e0f2e142c5d_680x532.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!1mUI!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feeaaf67b-b39b-4fd6-aefc-7e0f2e142c5d_680x532.webp" width="680" height="532" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/eeaaf67b-b39b-4fd6-aefc-7e0f2e142c5d_680x532.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:532,&quot;width&quot;:680,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;star schema example dimodelo&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="star schema example dimodelo" title="star schema example dimodelo" srcset="/__u/substackcdn.com/image/fetch/$s_!1mUI!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feeaaf67b-b39b-4fd6-aefc-7e0f2e142c5d_680x532.webp 424w, /__u/substackcdn.com/image/fetch/$s_!1mUI!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feeaaf67b-b39b-4fd6-aefc-7e0f2e142c5d_680x532.webp 848w, /__u/substackcdn.com/image/fetch/$s_!1mUI!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feeaaf67b-b39b-4fd6-aefc-7e0f2e142c5d_680x532.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!1mUI!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feeaaf67b-b39b-4fd6-aefc-7e0f2e142c5d_680x532.webp 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">star schema</figcaption></figure></div><p>The Star schema is used because of these characteristics:</p><ul><li><p>The <a href="/__u/dimodelo.substack.com/p/what-is-a-star-schema-and-why-its-important/">Star Schema</a> is an easy-to-understand and navigate data model that supports multiple analytic use cases.</p></li><li><p>Because of its simplified joins, a Star Schema supports high-performance aggregated queries. It performs well over many different analytics use cases.</p></li><li><p>Star schemas are broadly accepted and used across the industry.</p></li><li><p>The Star schema is the schema expected by&nbsp;Semantic layer&nbsp;tools. The semantic layer can consume Star Schemas as-is and apply various compression and pre-aggregation techniques to further enhance aggregated analytical query performance.</p></li></ul><p>Because of the nature of the Star schema, it is easy to implement standardized patterns to load Facts and Dimensions. Check out our <a href="/__u/dimodelo.substack.com/p/slowly-changing-dimension/">Slowly Changing Dimension article</a> for an example.</p><p>Modern data platforms such as Databricks, Snowflake, and Microsoft Fabric provide procedural languages like SQL and Python that can be used to implement the entities in the Presentation layer.</p><h3>Semantic Layer</h3><p>The semantic layer is typically exposed to end users for business intelligence, ad-hoc analysis, reporting, and dashboard use cases. End users interact with the semantic layer via visualization tools like PowerBI or Tableau.</p><p>A semantic layer is implemented in a technology that facilitates high-performance aggregated queries over large amounts of data.</p><p>The semantic layer&#8217;s data model mirrors the presentation layer&#8217;s Star Schema. It further augments the data model with calculated measures and hierarchies that other technologies cannot create.</p><p>There are several styles of Semantic layers, including materialized, virtual or hybrid. There are also various tools and vendors. PowerBI implements a semantic layer. Other materialized/hybrid semantic layers include Kyligence, GoodData,&nbsp;<a href="https://druid.apache.org/">Apache Druid</a>&nbsp;and Apache Pinot. Some virtual/hybrid semantic layers include Cube, Malloy, LookML, Metriql, AtScale, MetricFlow, Metlo, and Denodo.</p><p>The Ralph Kimball approach to Data Warehouse architecture focuses on creating smaller data marts optimized for specific business areas with conformed dimensions unifying the data marts. Practically speaking, the value of a data mart is to present a subset of the data warehouse that only includes data relevant to a business area or user group. This can be achieved by developing multiple semantic models. The added advantage is the ability to apply security at the semantic model level.</p><p>Read a <a href="/__u/dimodelo.substack.com/p/what-is-a-semantic-layer-what-why-how-and-more/">deep dive into semantic layers</a> for further information.</p><h3>Visualization Layer</h3><p>The visualization layer of the data warehouse refers to the set of tools and technologies used to present and visualize the data stored within the presentation/semantic layer of the data warehouse. You deliver meaningful insights through various forms of visual representation, enabling users to understand trends, patterns, and relationships in the data. Components of the visualization layer typically include:</p><ul><li><p><strong>Dashboards</strong>: Interactive, real-time interfaces displaying key metrics and performance indicators through charts, graphs, and gauges.</p></li><li><p><strong>Reports</strong>: Predefined and ad-hoc reports that present data in a structured format, often with tables, charts, and summaries.</p></li><li><p><strong>Data Visualization Tools</strong>: Software that allows users to self-serve, creating custom dashboards and reports.</p></li><li><p><strong>Ad hoc Analysis tools</strong> facilitate multidimensional analysis, often providing pivot tables and drill-down capabilities that enable users to explore data and generate insights.</p></li><li><p><strong>Business Intelligence Portal</strong>: Providing online access to reports and dashboards, organised in relevant folders, groups and departments. User and developers can publish their reports to the Portal, making them available for others to use. The portal provides safeguards like access control.</p></li></ul><p>Examples of popular tools used in the visualization layer include Tableau, Power BI, Looker, and QlikView. These tools provide user-friendly interfaces that enable business users, analysts, and decision-makers to interact with and interpret the data effectively.</p><p>A Visualization layer won&#8217;t typically store data. It simply queries and presents the data from the presentation/semantic layers.</p><h2>ETL/Data Integration</h2><p>&#8220;ETL,&#8221; is an acronym for Extract, Transform, Load. It describes the process of extracting data out of one data store transforming it, and loading it into another.</p><p>Initially, data warehousing comprised only two layers: Staging and presentation. At the time, ETL referred to the process of extracting data from its origin, transforming it to fit the star schema, and then loading it into the Presentation Layer. Although the term ETL is still used today, it&#8217;s difficult to neatly apply the concept to the multiple layers of modern data warehouse architecture. In reality, every layer has some aspect of extract, transform and load. Nonetheless, the ETL terminology endures, and we continue to use it when describing the movement of data through the various layers.</p><p>Some people characterize ETL in modern data warehouses as data extracted from source systems, transformed into a Modelled layer, and then loaded into the Presentation layer. However, this description does not really depict the reality of the ETL system.</p><p>Instead, in the modern data warehouse architecture, I like to think of each Layer having its own mini ETL process:</p><ul><li><p><strong>Landing Layer</strong>. Data is <strong>extracted </strong>from the source and <strong>loaded </strong>into the Landing data store.</p></li><li><p><strong>Staging Layer</strong>. Data is<strong> extracted </strong>(or, more precisely, queried) from the Landing layer, lightly <strong>transformed </strong>into tabular format (with history), and <strong>loaded </strong>into the Staging layer datastore.</p></li><li><p><strong>Modelled Layer</strong>. Data is <strong>extracted </strong>(or, more precisely, queried) from the Staging Layer, <strong>transformed </strong>into a subject-orientated and <strong>loaded </strong>into the Modelled layer data store.</p></li><li><p><strong>Presentation Layer</strong>. Data is <strong>extracted </strong>(or, more precisely, queried) from the Modelled Layer, transformed into a star schema, and loaded into the Modelled Layer data store.</p></li><li><p><strong>Semantic Layer</strong>. Data is simply loaded into a Materialized Semantic Layer. Data is not loaded into a Virtual Semantic Layer.</p></li></ul><p>I think this description more accurately reflects the reality.</p><p>In the following sections, I&#8217;ll discuss Extract, Transform and Load in more detail.</p><h3>Extract</h3><p>As I&#8217;ve discussed, every layer of the modern data warehouse architecture has its own version of &#8220;extract&#8221;, but in this section, I want to focus on the process of extracting data from a source system and loading it into a Landing layer data store.</p><p>A core part of your technical Data Warehouse architecture will be the tool you use to implement data extraction from source systems. Generally, these tools specialize in extraction and exist in your architecture purely to fulfil that role (i.e. separation of concerns). All these tools should have these features:</p><ul><li><p>Ability to connect to a broad array of source systems and databases (usually in the hundreds).</p></li><li><p>The capability to support either batch, data streaming, or both methods of extracting data. Batch is the most common method for Data Warehouses. It involves scheduled extraction of multiple rows of data (i.e., batches) in bulk. Batch extraction is reasonably straightforward and easily understood. Streaming involves continuous real-time or near real-time &#8220;streaming&#8221; of individual source system transactions. Streaming is more difficult to implement and maintain but may be necessary to support real-time analytics and reverse ETL use cases.</p></li><li><p>Support a variety of extract patterns like Full, Incremental, Range and Change Tracking.</p></li><li><p>Ability to load data into various target datastores (e.g. <a href="https://aws.amazon.com/s3/">AWS S3</a>, Azure Storage) in a standardised format (e.g. parquet, CSV, JSON).</p></li><li><p>Support Scheduling, restart and recovery.</p></li><li><p>Support workflow monitoring.</p></li></ul><p>There are many dedicated Extraction tools. Some examples are <a href="https://airbyte.com/home-version-b?_stsgnoredir=1&amp;_configname=homepage_test_3">Airbyte</a>, <a href="https://www.singer.io/">Singer.io</a>, Kafka, Fivetran or Qlik.</p><h3>Transform</h3><p>In the early days of Data Warehouses, there was only one &#8220;transformation&#8221; step from the Staging layer to the Presentation Layer. Today, there are multiple transforms, from Landing to Staging (a very light transformation), Staging to the Modelled Layer, and Modelled Layer to Persistent Layer.</p><p>Transformation is the code that is written and executed to transform the data from one layer&#8217;s schema/format to another. It typically includes a combination of:</p><ul><li><p>Matching entities across various source systems</p></li><li><p>Merging data from multiple entities across multiple source systems into a single entity</p></li><li><p>Joining data across entities</p></li><li><p>Cleansing data, identifying and correcting errors, inconsistencies, and inaccuracies.</p></li><li><p>Summarizing data at higher grains</p></li><li><p>Denormalizing data into larger, consolidated tables, introducing redundancy to support simplified high-performance queries.</p></li><li><p>Remodeling data into a subject-oriented schema.</p></li></ul><p>Transformation is typically built within your core data platforms, such as Databricks, Snowflake, or Microsoft Fabric. These platforms provide procedural languages like SQL and Python that you can use to implement transformation logic. At Dimodelo, we recommend tools like &#8220;dbt,&#8221; which are platform-agnostic, provide data engineering automation, significantly reduce development time, and improve consistency.</p><h3>Load</h3><p>I confess that the L( i.e., Load)in ETL has often confused me. Isn&#8217;t it just a given that after you transform data, you load it into a data store? What&#8217;s the big deal? Well, it turns out that&#8217;s pretty much all there is to it!</p><p>Each layer in a modern data warehouse possesses its own &#8220;Load,&#8221; which results from a transformation process. Typically, the target is a single entity within a layer, usually a table in the Staging, Modelled and Presentation layers. Within the Landing layer, an entity is often implemented as a folder that receives all the extracted files corresponding to an entity from the source.</p><p>Loading a materialized Semantic layer is generally straightforward. The tool used to implement the Semantic layer will be able to load data, either incrementally or in full, directly from the Presentation Layer.</p><h2>Data Warehouse Architecture Components</h2><p>If you are going to implement a data warehouse, there are several technical/software components you need to consider:</p><ul><li><p><strong>Landing Data Store</strong>: A temporary storage area where raw data is initially landed before processing; examples include Amazon S3 and Azure Data Lake.</p></li><li><p><strong>Data Extraction Tool</strong>: Software that pulls data from various source systems into the data warehouse. Some examples are <a href="https://airbyte.com/home-version-b?_stsgnoredir=1&amp;_configname=homepage_test_3">Airbyte</a>, <a href="https://www.singer.io/">Singer.io</a>, Kafka, Fivetran or Qlik.</p></li><li><p><strong>Data Platform</strong>: The foundational infrastructure that processes and stores data within the data warehouse, often including databases and processing frameworks. The compute and storage within the Data Platform are often managed separately and can scale independently. Examples include Snowflake, Databricks, Google BigQuery, and Microsoft Fabric.</p></li><li><p><strong>Semantic Layer Tool</strong>: A tool that facilitates high-performance aggregated queries over large amounts of data; examples include AtScale and PowerBI.</p></li><li><p><strong>Business Intelligence Tool</strong>: Software that allows users to visualize and analyze data through reports and dashboards; examples include Tableau, Power BI, and Looker.</p></li><li><p><strong>Development</strong>:</p><ul><li><p><strong>Code Repository</strong>: A version-controlled storage space for source code and development artifacts, enabling collaborative development and change tracking; examples include GitHub, GitLab, Azure DevOps and Bitbucket.</p></li><li><p><strong>Agile Management Tool</strong>: Software that supports Agile project management methodologies, facilitating sprint planning, tracking, and collaboration; examples include Jira, Trello, and Azure DevOps.</p></li><li><p><strong>Data Warehouse Automation Tool</strong>: A tool that automates the transformation of data within the warehouse, enabling modular and maintainable data workflows; dbt (Data Build Tool) is an example.</p></li></ul></li><li><p><strong>Scheduling and Monitoring Tool: </strong>Software that manages and monitors data workflows, ensuring that tasks are executed at the right time and in the right order and provides user monitoring of progress. Examples include Apache Airflow and dbt.</p></li><li><p><strong>Network, Security, and Access Control</strong>: Mechanisms and tools to ensure secure data transmission, protect data from unauthorized access, and manage user permissions; examples include AWS IAM, Azure Active Directory, and Okta.</p></li><li><p><strong>Reference Data Management</strong>: The process of managing data lists for analytics classification or mapping purposes. It can be as simple as storing .csv files or as complex as master data management systems like Ataccama.</p></li><li><p><strong>Data Quality Management and Reporting</strong>: Tools and processes to ensure that data meets quality standards, with capabilities for profiling, cleansing, and reporting.</p></li></ul><h2>Extending the Data Warehouse Architecture</h2><h3>Data science and Machine Learning</h3><p>The <a href="https://www.datanami.com/2020/07/06/data-prep-still-dominates-data-scientists-time-survey-finds/">number one complaint Data Scientists</a> make is how much time they need to spend sourcing and transforming data to prepare it for input into their data science models. With the modern data warehouse architecture, it&#8217;s possible to unburden Data Scientists from the chore of sourcing data and instead allow them to concentrate on building insightful models.</p><p>Having data from multiple source systems consolidated in one location, such as a data platform, and ensuring it is current is beneficial for data scientists. Ideally, data science models should utilize the &#8220;Modelled&#8221; layer, where data integration and standard business rules have been applied, enhancing consistency with business operations. However, as the Data Warehouse may often be under development, it is permissible to construct data science models from the Persistent Staging layer. When dealing with unstructured data, which commonly resides only in the Landing layer, it is also acceptable for data science models to derive their data from this layer.</p><p>Modern data platforms like Databricks, Snowflake and Fabric are integrated with machine learning frameworks, allowing data science models to be trained, deployed, and monitored directly within the data platform. By extending the data platform with capabilities such as machine learning, automated feature selection, and seamless integration with visualization tools, organizations can empower data scientists to experiment and iterate rapidly. This alignment between data warehousing and data science ensures that models are built on the most up-to-date data and that insights can be operationalized quickly, driving more informed decision-making across the enterprise.</p><h3>Data Integration/Reverse ETL</h3><p>Traditionally, Data Integration teams responsible for the system interoperability of operational systems built completely separate data infrastructure and integration workflows to the data warehousing team. In recent years, people have recognized that there is a lot of cross-over in the work data integration and data warehousing teams do. This includes sourcing and transforming data in very similar ways. There is an acknowledgement that the Bronze and Silver layers of a modern data warehouse could be used as the source and transform processes for Data integration.</p><p>The modern data warehouse can consolidate the efforts of the data integration and warehousing teams into a centralized data &#8220;hub&#8221;. More specifically, the modern data warehouse can be used to source and transform data, which is then used as both a source of the presentation layer of a data warehouse and of operational system interoperability through data integration.</p><p>This does pose some challenges, as the timeliness requirements of data integration can be near real-time, making the landing and staging processes more difficult to engineer. In these cases, an ETL tool with streaming capabilities would be required.</p><p>The buzzword for this kind of data integration is &#8220;Reverse ETL&#8221;, which is the process of moving data from a data warehouse back into operational systems like CRM, marketing, and sales platforms. Reverse ETL includes the concept of taking the enriched data from the Presentation Layer or Semantic Layer of the data warehouse and pushing it back into the tools where end-users can act on it.</p><h3>Real-time analytics</h3><p>Real-time analytics sources, transforms, and analyzes data as soon as it is generated, enabling immediate insights and actions. Unlike traditional analytics, which often rely on batch processing, real-time analytics operates continuously, providing up-to-the-moment insights. This capability is crucial in scenarios where timely decision-making is essential, such as fraud detection, recommendation systems, or IoT device monitoring.</p><p>The need for real-time analytics has a significant impact on the architecture of modern data warehouses. Traditional data warehouses, designed primarily for batch processing, are not inherently equipped for the low-latency requirements of real-time data processing. To accommodate real-time analytics, modern data warehouse architectures often integrate technologies like streaming data tools that enable the ingestion, processing, and querying of data in real-time (e.g., Apache Kafka, Amazon Kinesis) and in-memory processing engines (e.g., Apache Flink, Apache Spark).</p>]]></content:encoded></item><item><title><![CDATA[What is a Star Schema (and why it’s important)]]></title><description><![CDATA[A Star Schema is a data modelling technique used to model the presentation layer of a Data Warehouse. It refers to the way Facts and Dimensions in the model are related.]]></description><link>https://dimodelo.substack.com/p/what-is-a-star-schema-and-why-its-important</link><guid isPermaLink="false">https://dimodelo.substack.com/p/what-is-a-star-schema-and-why-its-important</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Thu, 18 Jul 2024 22:14:40 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/77fe557f-909d-4e23-a4d7-89b3b28919aa_680x532.webp" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>A Star Schema is a data modelling technique used to model the presentation layer of a <a href="/__u/dimodelo.substack.com/p/what-is-a-data-warehouse-and-why-you-need-one/">Data Warehouse</a>. It refers to the way <a href="/__u/dimodelo.substack.com/p/what-is-a-fact-table-and-why-you-need-them/">Facts</a> and <a href="/__u/dimodelo.substack.com/p/dimension-tables-an-introduction/">Dimensions</a> in the model are related. A Star Schema is organized around a central fact table that is related to its Dimension tables using foreign keys in the Fact table.</p><p>The name &#8220;Star&#8221; schema refers to the star-like pattern that emerges when you present the Fact table and its Dimensions in an entity-relationship diagram.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!eGaX!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7ff1635f-6c70-44fa-b40b-000d621653ce_680x532.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!eGaX!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7ff1635f-6c70-44fa-b40b-000d621653ce_680x532.webp 424w, /__u/substackcdn.com/image/fetch/$s_!eGaX!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7ff1635f-6c70-44fa-b40b-000d621653ce_680x532.webp 848w, /__u/substackcdn.com/image/fetch/$s_!eGaX!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7ff1635f-6c70-44fa-b40b-000d621653ce_680x532.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!eGaX!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7ff1635f-6c70-44fa-b40b-000d621653ce_680x532.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!eGaX!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7ff1635f-6c70-44fa-b40b-000d621653ce_680x532.webp" width="680" height="532" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/7ff1635f-6c70-44fa-b40b-000d621653ce_680x532.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:532,&quot;width&quot;:680,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;star schema example&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="star schema example" title="star schema example" srcset="/__u/substackcdn.com/image/fetch/$s_!eGaX!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7ff1635f-6c70-44fa-b40b-000d621653ce_680x532.webp 424w, /__u/substackcdn.com/image/fetch/$s_!eGaX!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7ff1635f-6c70-44fa-b40b-000d621653ce_680x532.webp 848w, /__u/substackcdn.com/image/fetch/$s_!eGaX!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7ff1635f-6c70-44fa-b40b-000d621653ce_680x532.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!eGaX!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7ff1635f-6c70-44fa-b40b-000d621653ce_680x532.webp 1456w" sizes="100vw" fetchpriority="high"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">shows viewed star schema</figcaption></figure></div><p>The image above is an <strong>example of a Star Schema</strong>. It depicts an imaginary video streaming company, GetFlix, and a &#8220;Shows Viewed&#8221; Fact table. The &#8220;Shows Viewed&#8221; fact table is at the centre of the star schema and surrounded by its Dimensions, which form the points of the &#8220;star.&#8221;</p><h2>Benefits of Star Schemas</h2><p>A Star Schema focuses on delivering simplicity and query performance for the end user. The benefits include:</p><ul><li><p>It is easy for users to understand and navigate. Users can easily find and use the data they need for reporting and ad hoc analysis.</p></li><li><p>Because of its simplified joins, a Star Schema supports high-performance aggregated queries. It performs well over many different analytics use cases.</p></li><li><p>Broadly accepted and used across the industry.</p></li><li><p>The source schema expected by <a href="/__u/dimodelo.substack.com/p/what-is-a-semantic-layer-what-why-how-and-more/">Semantic layer</a> tools. These tools can consume Star Schemas as is and apply various compression and pre-aggregation techniques to further enhance aggregated analytical query performance.</p></li><li><p>The source schema expected by visualization tools like PowerBI and Tableau. They support these tools&#8217; drag-and-drop nature.</p></li><li><p>Eliminates issues present in &#8220;third normal form&#8221; (3NF) schemas, where multiple alternate join paths can produce different or incorrect query results from the same data. For example, in a Star schema, there is only one way to join &#8220;Shows Viewed&#8221; to Customer, whereas in a 3NF schema, there may be multiple ways to join from &#8220;Shows Viewed&#8221; to Customer.</p></li></ul><h2>The 3 essential building blocks of a Star Schema</h2><p>A Star Schema consists of two types of tables (Facts and Dimensions) and their relationships. Thus, it&#8217;s simplicity.</p><p>The following is a brief introduction to these concepts.</p><h3>Facts tables</h3><p>A Fact table represents a business process or an event in a business process. It contains the measures/numbers you want to analyse. For example, the &#8220;GetFlix&#8221; &#8220;Shows Viewed&#8221; fact table depicted in the star schema example below contains one row for every time a customer views an Episode of a Show. &#8220;Customer views an Episode of a Show&#8221; is the business event we are measuring.</p><p>Read <a href="/__u/dimodelo.substack.com/p/what-is-a-fact-table-and-why-you-need-them/">more about Fact Tables</a>.</p><h3>Dimensions</h3><p>A Dimension represents a business entity, which is the people, places, and things that come together to perform business activities. A Dimension contains the attributes (i.e. fields) of the business entity, e.g., Customer Gender, Age, Category, etc. The attributes are used to filter and group fact data when performing data warehousing queries. Attributes values should be descriptive values rather than codes (e.g. &#8220;Male&#8221; instead of &#8220;M&#8221;). The reason is that attribute values become column headings in a report. A column heading of &#8220;M&#8221; is not very informative.</p><p>This demonstrates one of the key differences between a Star Schema and a 3NF schema. A Dimension contains descriptive attributes and a lot of data redundancy. It doesn&#8217;t follow the conventional ideas of 3rd normal form (3NF) modelling. It is like this on purpose. That is often a hurdle that DBAs and application developers, coming from a traditional database background, need to overcome before they can fully embrace&nbsp;<a href="/__u/dimodelo.substack.com/p/what-is-dimensional-modeling-introduction/">Dimensional modelling concepts</a>.</p><p>Read <a href="/__u/dimodelo.substack.com/p/dimension-tables-an-introduction/">more about Dimensions</a>.</p><h3>Star Schema Relationships</h3><p>A Star Schema is a simplified model suitable for reporting and analytics with easy relationship navigation for end users. The image below depicts the relationship between a Fact and a Dimension.</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!ofIv!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F8e397ade-d05f-465c-8fa8-0f2a8f30ef89_494x152.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!ofIv!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F8e397ade-d05f-465c-8fa8-0f2a8f30ef89_494x152.webp 424w, /__u/substackcdn.com/image/fetch/$s_!ofIv!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F8e397ade-d05f-465c-8fa8-0f2a8f30ef89_494x152.webp 848w, /__u/substackcdn.com/image/fetch/$s_!ofIv!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F8e397ade-d05f-465c-8fa8-0f2a8f30ef89_494x152.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!ofIv!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F8e397ade-d05f-465c-8fa8-0f2a8f30ef89_494x152.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!ofIv!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F8e397ade-d05f-465c-8fa8-0f2a8f30ef89_494x152.webp" width="494" height="152" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/8e397ade-d05f-465c-8fa8-0f2a8f30ef89_494x152.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:152,&quot;width&quot;:494,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;star schema fact and dimension relationships&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="star schema fact and dimension relationships" title="star schema fact and dimension relationships" srcset="/__u/substackcdn.com/image/fetch/$s_!ofIv!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F8e397ade-d05f-465c-8fa8-0f2a8f30ef89_494x152.webp 424w, /__u/substackcdn.com/image/fetch/$s_!ofIv!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F8e397ade-d05f-465c-8fa8-0f2a8f30ef89_494x152.webp 848w, /__u/substackcdn.com/image/fetch/$s_!ofIv!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F8e397ade-d05f-465c-8fa8-0f2a8f30ef89_494x152.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!ofIv!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F8e397ade-d05f-465c-8fa8-0f2a8f30ef89_494x152.webp 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a><figcaption class="image-caption">star schema dimensional relationships</figcaption></figure></div><p>The rules for relationships are very simple. The direction of a relationship is always from a Fact to a Dimension. That is, the Fact contains the foreign key to the Dimension. The cardinality is always 1 to many. A Fact is related to only 1 Dimension row, but a Dimension row can be related to many Fact rows. There are many-to-many joins, but this is resolved through an intermediary &#8220;Group&#8221; Dimension and &#8220;Bridge&#8221; fact with two 1-to-many relationships. Read <a href="/__u/dimodelo.substack.com/p/modeling-many-to-many-relationships-in-a-star-schema/">more about dimensional many-to-many relationships</a>.</p><p>The best practice is to always have <a href="/__u/dimodelo.substack.com/p/dimension-tables-an-introduction/#Dimension-Surrogate-Key-vs-Business-Key">surrogate keys</a> on Dimensions. Therefore, the foreign key on the Fact table is related to the surrogate key of the dimension.</p><h2>Star Schema vs Snowflake Schema</h2><p>The Star and Snowflake schemas are two types of Dimensional modelling techniques used in Data Warehousing to organize and structure data for efficient querying and analysis.</p><p>Below is the model for a Sales Fact Star Schema vs. a Snowflake Schema for the same Fact.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!cGEx!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc83eca52-ce16-42e4-ae6c-1724e07fdb7c_702x378.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!cGEx!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc83eca52-ce16-42e4-ae6c-1724e07fdb7c_702x378.webp 424w, /__u/substackcdn.com/image/fetch/$s_!cGEx!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc83eca52-ce16-42e4-ae6c-1724e07fdb7c_702x378.webp 848w, /__u/substackcdn.com/image/fetch/$s_!cGEx!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc83eca52-ce16-42e4-ae6c-1724e07fdb7c_702x378.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!cGEx!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc83eca52-ce16-42e4-ae6c-1724e07fdb7c_702x378.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!cGEx!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc83eca52-ce16-42e4-ae6c-1724e07fdb7c_702x378.webp" width="702" height="378" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/c83eca52-ce16-42e4-ae6c-1724e07fdb7c_702x378.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:378,&quot;width&quot;:702,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;sales_fact_customer_star_schema&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="sales_fact_customer_star_schema" title="sales_fact_customer_star_schema" srcset="/__u/substackcdn.com/image/fetch/$s_!cGEx!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc83eca52-ce16-42e4-ae6c-1724e07fdb7c_702x378.webp 424w, /__u/substackcdn.com/image/fetch/$s_!cGEx!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc83eca52-ce16-42e4-ae6c-1724e07fdb7c_702x378.webp 848w, /__u/substackcdn.com/image/fetch/$s_!cGEx!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc83eca52-ce16-42e4-ae6c-1724e07fdb7c_702x378.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!cGEx!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc83eca52-ce16-42e4-ae6c-1724e07fdb7c_702x378.webp 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Star Schema</figcaption></figure></div><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!NHfc!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fdeae9536-66ed-47d6-9367-223149e32a12_768x452.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!NHfc!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fdeae9536-66ed-47d6-9367-223149e32a12_768x452.webp 424w, /__u/substackcdn.com/image/fetch/$s_!NHfc!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fdeae9536-66ed-47d6-9367-223149e32a12_768x452.webp 848w, /__u/substackcdn.com/image/fetch/$s_!NHfc!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fdeae9536-66ed-47d6-9367-223149e32a12_768x452.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!NHfc!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fdeae9536-66ed-47d6-9367-223149e32a12_768x452.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!NHfc!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fdeae9536-66ed-47d6-9367-223149e32a12_768x452.webp" width="768" height="452" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/deae9536-66ed-47d6-9367-223149e32a12_768x452.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:452,&quot;width&quot;:768,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;snowflake schema&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="snowflake schema" title="snowflake schema" srcset="/__u/substackcdn.com/image/fetch/$s_!NHfc!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fdeae9536-66ed-47d6-9367-223149e32a12_768x452.webp 424w, /__u/substackcdn.com/image/fetch/$s_!NHfc!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fdeae9536-66ed-47d6-9367-223149e32a12_768x452.webp 848w, /__u/substackcdn.com/image/fetch/$s_!NHfc!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fdeae9536-66ed-47d6-9367-223149e32a12_768x452.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!NHfc!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fdeae9536-66ed-47d6-9367-223149e32a12_768x452.webp 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Snowflake Schema</figcaption></figure></div><p>In the Star schema example, the Product Dimension contains an attribute for the &#8220;Brand&#8221; of the Product, whereas the Snowflake schema has a separate Brand Dimension with a &#8220;snowflake&#8221; relationship to the Product Dimension. This is the crucial difference between the Star Schema and the Snowflake Schema. In the Snowflake schema, attributes are normalised into separate Dimensions, whereas they are Denormalised in the Star Schema. The same data exists in the models; just where it is stored is different.</p><p>The only advantage of Snowflake Schema is less storage, and in the modern data warehouse, storage is no longer an issue, especially considering Dimensions are usually relatively small compared to Facts. The Star Schema is easier to design and maintain, is easier to understand and navigate, and offers faster performance.</p><p>Our recommendation is <strong>never to use the Snowflake Schema</strong>.</p><p>Read <a href="/__u/dimodelo.substack.com/p/star-schema-vs-snowflake-schema/">more about Star schema vs Snowflake schema</a>.</p><h2>Star Schemas and Conformed Dimensions</h2><p>So far, we have discussed using a Star Schema. However, a Star Schema only describes the model for a single Fact table. An Enterprise data warehouse should model many different business processes/events, each with its own Fact table and related Dimensions.</p><p>The question is, how do we prevent duplication of the Dimensions used by Facts and facilitate cross-business process analysis?</p><p>The answer is &#8220;Conformed&#8221; Dimensions. Essentially, a conformed Dimension is a Dimension shared by many Facts. Typical conformed Dimensions are key business entities like Employees, Customers, Products, Cost Centres, Dates, and Times. Conformed Dimensions are the &#8220;links&#8221; between multiple Star Schema models.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!sFED!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0fbe1d58-4481-42d1-90cc-b67118e91783_750x566.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!sFED!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0fbe1d58-4481-42d1-90cc-b67118e91783_750x566.webp 424w, /__u/substackcdn.com/image/fetch/$s_!sFED!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0fbe1d58-4481-42d1-90cc-b67118e91783_750x566.webp 848w, /__u/substackcdn.com/image/fetch/$s_!sFED!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0fbe1d58-4481-42d1-90cc-b67118e91783_750x566.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!sFED!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0fbe1d58-4481-42d1-90cc-b67118e91783_750x566.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!sFED!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0fbe1d58-4481-42d1-90cc-b67118e91783_750x566.webp" width="750" height="566" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/0fbe1d58-4481-42d1-90cc-b67118e91783_750x566.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:566,&quot;width&quot;:750,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;star schemas with conformed dimensions&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="star schemas with conformed dimensions" title="star schemas with conformed dimensions" srcset="/__u/substackcdn.com/image/fetch/$s_!sFED!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0fbe1d58-4481-42d1-90cc-b67118e91783_750x566.webp 424w, /__u/substackcdn.com/image/fetch/$s_!sFED!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0fbe1d58-4481-42d1-90cc-b67118e91783_750x566.webp 848w, /__u/substackcdn.com/image/fetch/$s_!sFED!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0fbe1d58-4481-42d1-90cc-b67118e91783_750x566.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!sFED!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0fbe1d58-4481-42d1-90cc-b67118e91783_750x566.webp 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Enterprise data warehouse with conformed dimensions (in red)</figcaption></figure></div><p>When two Fact tables share a Dimension, you can produce a report with measures side-by-side from both Fact tables, categorized or filtered by attributes of their conformed (i.e. shared) Dimensions. In this way, dimensional modelling with conformed Dimensions supports enterprise-wide cross-business process analysis.</p><p>Another way of representing conformed dimensions is through a <a href="https://www.dimodelo.com/blog/2023/what-is-a-data-warehouse-bus-matrix-and-why-you-need-one/">data warehouse matrix</a>.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!a4AS!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69cc148d-ca8c-4bf0-95fe-960293bd6419_697x374.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!a4AS!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69cc148d-ca8c-4bf0-95fe-960293bd6419_697x374.png 424w, /__u/substackcdn.com/image/fetch/$s_!a4AS!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69cc148d-ca8c-4bf0-95fe-960293bd6419_697x374.png 848w, /__u/substackcdn.com/image/fetch/$s_!a4AS!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69cc148d-ca8c-4bf0-95fe-960293bd6419_697x374.png 1272w, /__u/substackcdn.com/image/fetch/$s_!a4AS!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69cc148d-ca8c-4bf0-95fe-960293bd6419_697x374.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!a4AS!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69cc148d-ca8c-4bf0-95fe-960293bd6419_697x374.png" width="697" height="374" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/69cc148d-ca8c-4bf0-95fe-960293bd6419_697x374.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:374,&quot;width&quot;:697,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!a4AS!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69cc148d-ca8c-4bf0-95fe-960293bd6419_697x374.png 424w, /__u/substackcdn.com/image/fetch/$s_!a4AS!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69cc148d-ca8c-4bf0-95fe-960293bd6419_697x374.png 848w, /__u/substackcdn.com/image/fetch/$s_!a4AS!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69cc148d-ca8c-4bf0-95fe-960293bd6419_697x374.png 1272w, /__u/substackcdn.com/image/fetch/$s_!a4AS!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69cc148d-ca8c-4bf0-95fe-960293bd6419_697x374.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">example data warehouse bus matrix</figcaption></figure></div><h2>How to build a Star Schema</h2><p>Below is the image of the physical Fact table and its Dimensions, implemented in a relational database. The key thing to note is that each Dimension has a surrogate key, and the Fact table has a foreign key to each of those surrogate keys. You may be wondering why there are no physical relationships depicted. This is because, in this case, each table is implemented with a ColumnStore index, and no primary keys are defined. ColumnStore indexes are ideal for analytical style aggregated queries (basically an index on every attribute) and ETL bulk loads. Also, generally speaking, Primary Keys and Clustered indexes will slow down your ETL Load. The foreign to primary key relationships still exist but are not physically implemented.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!tgBk!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe54a437e-884f-459c-9ad3-7609d5ea8849_844x811.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!tgBk!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe54a437e-884f-459c-9ad3-7609d5ea8849_844x811.png 424w, /__u/substackcdn.com/image/fetch/$s_!tgBk!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe54a437e-884f-459c-9ad3-7609d5ea8849_844x811.png 848w, /__u/substackcdn.com/image/fetch/$s_!tgBk!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe54a437e-884f-459c-9ad3-7609d5ea8849_844x811.png 1272w, /__u/substackcdn.com/image/fetch/$s_!tgBk!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe54a437e-884f-459c-9ad3-7609d5ea8849_844x811.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!tgBk!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe54a437e-884f-459c-9ad3-7609d5ea8849_844x811.png" width="844" height="811" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/e54a437e-884f-459c-9ad3-7609d5ea8849_844x811.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:811,&quot;width&quot;:844,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;physical star schema&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="physical star schema" title="physical star schema" srcset="/__u/substackcdn.com/image/fetch/$s_!tgBk!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe54a437e-884f-459c-9ad3-7609d5ea8849_844x811.png 424w, /__u/substackcdn.com/image/fetch/$s_!tgBk!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe54a437e-884f-459c-9ad3-7609d5ea8849_844x811.png 848w, /__u/substackcdn.com/image/fetch/$s_!tgBk!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe54a437e-884f-459c-9ad3-7609d5ea8849_844x811.png 1272w, /__u/substackcdn.com/image/fetch/$s_!tgBk!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe54a437e-884f-459c-9ad3-7609d5ea8849_844x811.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>The full details of the above table schema can be found in the <a href="https://www.dimodelo.com/blog/2024/dimension-tables-an-introduction/">Dimension</a> and <a href="https://www.dimodelo.com/blog/2024/what-is-a-fact-table-and-why-you-need-them/">Fact</a> articles.</p><h2>Why you should use Star Schema in Visualization tools like PowerBI</h2><p>The Star Schema design is crucial for creating Power BI semantic models that are both high-performing and user-friendly.</p><p>Each visual in a Power BI report generates a query sent to the Power BI semantic model. These queries filter, group, and summarize the data within the model. An effectively designed model offers tables for filtering and grouping and tables for summarization. This aligns seamlessly with the star schema&#8217;s Dimensions and Facts. Dimensions support the filtering and grouping function, while Fact tables support&nbsp;summarization.</p><p>From a performance perspective, it has been <a href="https://www.sqlbi.com/articles/power-bi-star-schema-or-single-table/">proven that Star schemas are more performant than &#8220;flattened&#8221; &#8220;one big table&#8221; (OBT) tables</a> when used in PowerBI.</p><ul><li><p>The Star schema is much faster for retrieving values for columns in slicers. This is important for useability.</p></li><li><p>The Star Schema model is much smaller. Dimensional models are far more compressible. They consume less memory.</p></li><li><p>The Star Schema is faster for more complex queries, and when the flatted model is faster, it&#8217;s not by much. <a href="https://www.sqlbi.com/articles/header-detail-vs-star-schema-models-in-tabular-and-power-bi/">Performance is even worse for 3NF models</a>.</p></li><li><p>Furthermore, it&#8217;s been <a href="https://www.sqlbi.com/articles/the-importance-of-star-schemas-in-power-bi/">demonstrated that &#8220;flattened&#8221; tables can produce inaccurate numbers</a>.</p></li></ul><p>It&#8217;s likely that Tableau and other visualization tools experience the same results.</p><p>The conclusion here is that Star Schemas are the best schema to use in semantic models that support visualization tools.</p><h2>Star Schema vs 3rd Normal Form 3NF</h2><p>The star schema and third normal form (3NF) schema are both database design methodologies, but they serve different purposes and have distinct structures.</p><p>3NF is intended for use in operational (OLTP) systems where data integrity and minimization of redundancy are critical. It supports write-heavy operations, ensuring data consistency and efficiency in updates.</p><p>Tables are organized to eliminate redundancy and ensure that each piece of data is stored only once. Tables are normalized, which involves dividing data into multiple related tables.</p><p>3NF does not perform well for aggregated analytical queries due to the need to involve multiple tables with many joins. Tables are optimized for data integrity and efficient updates rather than read performance.</p>]]></content:encoded></item><item><title><![CDATA[Star Schema vs Snowflake Schema]]></title><description><![CDATA[The Star and Snowflake schemas are two types of Dimensional modelling techniques used in Data Warehousing to organize and structure data for efficient querying and analysis. How do Star and Snowflak..]]></description><link>https://dimodelo.substack.com/p/star-schema-vs-snowflake-schema</link><guid isPermaLink="false">https://dimodelo.substack.com/p/star-schema-vs-snowflake-schema</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Thu, 18 Jul 2024 06:43:27 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/ab81d679-7e9f-46c8-ad4f-4a1d0e81baed_702x378.webp" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>The Star and Snowflake schemas are two types of <a href="/__u/dimodelo.substack.com/p/what-is-dimensional-modeling-introduction/">Dimensional modelling</a> techniques used in Data Warehousing to organize and structure data for efficient querying and analysis. How do Star and Snowflake schemas differ, and which do we recommend? Read on to find out.</p><h2>Overview</h2><p>Below is the model for a Sales Fact Star Schema vs. a Snowflake Schema for the same Fact.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!geYW!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F82fdd4fe-8633-4ac6-891b-1b83d2307443_702x378.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!geYW!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F82fdd4fe-8633-4ac6-891b-1b83d2307443_702x378.webp 424w, /__u/substackcdn.com/image/fetch/$s_!geYW!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F82fdd4fe-8633-4ac6-891b-1b83d2307443_702x378.webp 848w, /__u/substackcdn.com/image/fetch/$s_!geYW!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F82fdd4fe-8633-4ac6-891b-1b83d2307443_702x378.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!geYW!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F82fdd4fe-8633-4ac6-891b-1b83d2307443_702x378.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!geYW!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F82fdd4fe-8633-4ac6-891b-1b83d2307443_702x378.webp" width="702" height="378" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/82fdd4fe-8633-4ac6-891b-1b83d2307443_702x378.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:378,&quot;width&quot;:702,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;sales_fact_customer_star_schema&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="sales_fact_customer_star_schema" title="sales_fact_customer_star_schema" srcset="/__u/substackcdn.com/image/fetch/$s_!geYW!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F82fdd4fe-8633-4ac6-891b-1b83d2307443_702x378.webp 424w, /__u/substackcdn.com/image/fetch/$s_!geYW!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F82fdd4fe-8633-4ac6-891b-1b83d2307443_702x378.webp 848w, /__u/substackcdn.com/image/fetch/$s_!geYW!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F82fdd4fe-8633-4ac6-891b-1b83d2307443_702x378.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!geYW!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F82fdd4fe-8633-4ac6-891b-1b83d2307443_702x378.webp 1456w" sizes="100vw" fetchpriority="high"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Star Schema</figcaption></figure></div><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!kh9I!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2fdc8e0a-9d3f-4d9f-9dea-102e7b73c78e_768x452.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!kh9I!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2fdc8e0a-9d3f-4d9f-9dea-102e7b73c78e_768x452.webp 424w, /__u/substackcdn.com/image/fetch/$s_!kh9I!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2fdc8e0a-9d3f-4d9f-9dea-102e7b73c78e_768x452.webp 848w, /__u/substackcdn.com/image/fetch/$s_!kh9I!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2fdc8e0a-9d3f-4d9f-9dea-102e7b73c78e_768x452.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!kh9I!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2fdc8e0a-9d3f-4d9f-9dea-102e7b73c78e_768x452.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!kh9I!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2fdc8e0a-9d3f-4d9f-9dea-102e7b73c78e_768x452.webp" width="768" height="452" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/2fdc8e0a-9d3f-4d9f-9dea-102e7b73c78e_768x452.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:452,&quot;width&quot;:768,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;snowflake schema&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="snowflake schema" title="snowflake schema" srcset="/__u/substackcdn.com/image/fetch/$s_!kh9I!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2fdc8e0a-9d3f-4d9f-9dea-102e7b73c78e_768x452.webp 424w, /__u/substackcdn.com/image/fetch/$s_!kh9I!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2fdc8e0a-9d3f-4d9f-9dea-102e7b73c78e_768x452.webp 848w, /__u/substackcdn.com/image/fetch/$s_!kh9I!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2fdc8e0a-9d3f-4d9f-9dea-102e7b73c78e_768x452.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!kh9I!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2fdc8e0a-9d3f-4d9f-9dea-102e7b73c78e_768x452.webp 1456w" sizes="100vw"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Snowflake Schema</figcaption></figure></div><p>In the <a href="/__u/dimodelo.substack.com/p/what-is-a-star-schema-and-why-its-important/">Star Schema</a> example, the Product <a href="/__u/dimodelo.substack.com/p/dimension-tables-an-introduction/">Dimension</a> contains an attribute for the &#8220;Brand&#8221; of the Product, whereas the Snowflake schema has a separate Brand Dimension with a &#8220;snowflake&#8221; relationship to the Product Dimension. This is the crucial difference between the Star Schema and the Snowflake Schema. In the Snowflake schema, attributes are normalised into separate Dimensions, whereas they are denormalised in the Star Schema. The same data exists in the models; just where it is stored is different.</p><p>How do Star Schemas differ from Snowflake Dimensions?</p><h3>Star Schema</h3><ol><li><p><strong>Structure</strong>:</p><ul><li><p>Central fact table surrounded by dimension tables.</p></li><li><p>Dimension tables are typically denormalized, containing all necessary attributes.</p></li></ul></li><li><p><strong>Relationships</strong>:</p><ul><li><p>Only direct one-to-many relationships between the Facts and Dimensions.</p></li></ul></li><li><p><strong>Simplicity</strong>:</p><ul><li><p>Easier for Users to understand and navigate when producing reports.</p></li><li><p>Queries are faster due to fewer joins needed between tables.</p></li></ul></li><li><p><strong>Normalization</strong>:</p><ul><li><p>More redundancy because dimension tables are not normalized, which can lead to larger storage requirements.</p></li></ul></li></ol><p>Read a detailed description of the Star Schema.</p><h3>Snowflake Schema</h3><ol><li><p><strong>Structure</strong>:</p><ul><li><p>Central fact table surrounded by normalized dimension tables.</p></li><li><p>Dimension tables are further normalized into multiple related Dimensions, resembling a snowflake.</p></li></ul></li><li><p><strong>Relationships</strong>:</p><ul><li><p>More complex relationships due to the normalization of Dimension tables.</p></li><li><p>Dimension tables can have relationships with other Dimension tables.</p></li></ul></li><li><p><strong>Simplicity:</strong></p><ul><li><p>More difficult to design and maintain.</p></li><li><p>More difficult for Users to understand and navigate.</p></li><li><p>Potentially slower query performance due to the need for more joins.</p></li></ul></li><li><p><strong>Normalization</strong>:</p><ul><li><p>Dimension tables are normalized, reducing redundancy and improving data integrity.</p></li><li><p>Queries may involve more joins due to the normalization.</p></li></ul></li></ol><h3>Comparison</h3><ul><li><p><strong>Design and Maintenance</strong>: Star schema is simpler and easier to design and maintain, while the snowflake schema is more complex but can offer better data integrity.</p></li><li><p><strong>Simplicity</strong>: Users find the Star Schema easier to understand and navigate. The Snowflake Cchema requires the User to navigate and use multiple joins to get data from a Fact.</p></li><li><p><strong>Query Performance</strong>: Star schema typically offers faster query performance because it requires fewer joins, while the snowflake schema might be slower due to the need for additional joins.</p></li><li><p><strong>Storage Requirements</strong>: Star schema usually requires more storage space due to denormalization, whereas the snowflake schema can be more efficient in terms of storage because of normalization.</p></li></ul><h2>Recommendation</h2><p>Our recommendation is <strong>never to use the Snowflake Schema</strong>. The only advantage is less storage, and in the modern data warehouse, storage is no longer an issue, especially considering Dimensions are usually relatively small compared to Facts. The Star schema is easier to design and maintain, easier to understand and navigate and offers faster performance.</p>]]></content:encoded></item><item><title><![CDATA[Modeling Many to Many Relationships in a Star Schema]]></title><description><![CDATA[Many to Many relationships are defined in a Star Schema Dimensional model using a &#8220;Group&#8221; Dimension and a &#8220;Bridge&#8221; Fact. Take the example below:]]></description><link>https://dimodelo.substack.com/p/modeling-many-to-many-relationships-in-a-star-schema</link><guid isPermaLink="false">https://dimodelo.substack.com/p/modeling-many-to-many-relationships-in-a-star-schema</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Wed, 17 Jul 2024 07:59:06 GMT</pubDate><enclosure url="https://substackcdn.com/image/fetch/$s_!Ee_C!,w_256,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F051177eb-7dd5-477a-8799-237c8425c504_216x216.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>Many to Many relationships are defined in a <a href="/__u/dimodelo.substack.com/p/what-is-a-star-schema-and-why-its-important/">Star Schema</a> Dimensional model using a &#8220;Group&#8221; <a href="/__u/dimodelo.substack.com/p/dimension-tables-an-introduction/">Dimension</a> and a &#8220;Bridge&#8221; <a href="/__u/dimodelo.substack.com/p/what-is-a-fact-table-and-why-you-need-them/">Fact</a>. Take the example below:</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!gR74!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feb96cc81-fcb2-4159-b398-d547b6cd89ab_910x145.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!gR74!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feb96cc81-fcb2-4159-b398-d547b6cd89ab_910x145.png 424w, /__u/substackcdn.com/image/fetch/$s_!gR74!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feb96cc81-fcb2-4159-b398-d547b6cd89ab_910x145.png 848w, /__u/substackcdn.com/image/fetch/$s_!gR74!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feb96cc81-fcb2-4159-b398-d547b6cd89ab_910x145.png 1272w, /__u/substackcdn.com/image/fetch/$s_!gR74!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feb96cc81-fcb2-4159-b398-d547b6cd89ab_910x145.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!gR74!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feb96cc81-fcb2-4159-b398-d547b6cd89ab_910x145.png" width="910" height="145" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/eb96cc81-fcb2-4159-b398-d547b6cd89ab_910x145.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:145,&quot;width&quot;:910,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!gR74!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feb96cc81-fcb2-4159-b398-d547b6cd89ab_910x145.png 424w, /__u/substackcdn.com/image/fetch/$s_!gR74!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feb96cc81-fcb2-4159-b398-d547b6cd89ab_910x145.png 848w, /__u/substackcdn.com/image/fetch/$s_!gR74!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feb96cc81-fcb2-4159-b398-d547b6cd89ab_910x145.png 1272w, /__u/substackcdn.com/image/fetch/$s_!gR74!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feb96cc81-fcb2-4159-b398-d547b6cd89ab_910x145.png 1456w" sizes="100vw" fetchpriority="high"></picture><div></div></div></a></figure></div><p>In the above example, an insurance company receives medical claims. The medical claims are the business event represented by the <a href="https://www.dimodelo.com/blog/2024/what-is-a-fact-table-and-why-you-need-them/">Fact table</a>. Each medical claim can have more than one associated diagnosis. These groups of associated diagnoses are modelled in a &#8220;Group&#8221; dimension. Individual diagnoses are associated with the &#8220;Group&#8221; Dimension via a &#8220;Bridge&#8221; fact. The &#8220;Bridge&#8221; fact makes the association between the &#8220;Group&#8221; and individual diagnosis.</p><p>In this scenario, the most challenging thing to build is the &#8220;Group&#8221;. It doesn&#8217;t exist in your source and must be derived. To do this, you need to select all combinations of diagnoses that exist in medical claims. The source of the target fact will usually be the source of your &#8220;Group&#8221; as well.&nbsp;For example,&nbsp;Let&#8217;s say you had these groups of diagnoses that are used on claims.</p><ul><li><p>A,B</p></li><li><p>C,D</p></li><li><p>A,D</p></li><li><p>B,E</p></li></ul><p>Then, there would be one row in the Group Dimension for each Group. In fact, the concatenation of diagnosis keys is an excellent candidate to use as the business key of the Dimension, i.e. DiagnosisGroup_Id. You may also want to include a concatenation of the diagnosis names as an attribute if you want to analyze the impact of certain diagnosis combinations. For example, by choosing the &#8220;C,D&#8221; &#8220;Group&#8221; Dimension member, an analyst can quickly get the claims measures for claims with both C and D, but only C &amp; D diagnoses.</p><p>The Bridge is simply another Fact, usually a Fact-less Fact, that just records the existence of individual diagnoses within the group. However, it is possible to put measures on this Bridge. For example, a ratio of the contribution of each individual Diagnosis in the Group to the overall value of the claim. A measure on a bridge is usually some ratio between the individuals. Another example is the ratio of ownership of joint buyers on a Sale.</p><p>A Group isn&#8217;t always derived, as shown in the example below:</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!xLnA!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb0322583-7171-414d-b9c6-6f3156bc0b3b_909x103.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!xLnA!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb0322583-7171-414d-b9c6-6f3156bc0b3b_909x103.png 424w, /__u/substackcdn.com/image/fetch/$s_!xLnA!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb0322583-7171-414d-b9c6-6f3156bc0b3b_909x103.png 848w, /__u/substackcdn.com/image/fetch/$s_!xLnA!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb0322583-7171-414d-b9c6-6f3156bc0b3b_909x103.png 1272w, /__u/substackcdn.com/image/fetch/$s_!xLnA!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb0322583-7171-414d-b9c6-6f3156bc0b3b_909x103.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!xLnA!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb0322583-7171-414d-b9c6-6f3156bc0b3b_909x103.png" width="909" height="103" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/b0322583-7171-414d-b9c6-6f3156bc0b3b_909x103.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:103,&quot;width&quot;:909,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!xLnA!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb0322583-7171-414d-b9c6-6f3156bc0b3b_909x103.png 424w, /__u/substackcdn.com/image/fetch/$s_!xLnA!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb0322583-7171-414d-b9c6-6f3156bc0b3b_909x103.png 848w, /__u/substackcdn.com/image/fetch/$s_!xLnA!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb0322583-7171-414d-b9c6-6f3156bc0b3b_909x103.png 1272w, /__u/substackcdn.com/image/fetch/$s_!xLnA!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb0322583-7171-414d-b9c6-6f3156bc0b3b_909x103.png 1456w" sizes="100vw"></picture><div></div></div></a></figure></div><p>In the example above, a Bank Account has joint Account Holders (Customers). There is no need to derive the Group as it exists as an entity in your source.</p><p>Another example might be if you had a Fact that represented the process of a Customer viewing a show on a streaming service. A show is related to many Actors, but the Group is readily available in the source system as a Cast entity that already groups the Actors. In this case, the &#8220;Cast&#8221; entity can be used as the source of the &#8220;Group&#8221; Dimension.</p><p>Why are Many to Many relationships modelled this way? One reason is that OLAP Cubes and other <a href="/__u/dimodelo.substack.com/p/what-is-a-semantic-layer-what-why-how-and-more/">semantic layer software</a> recognize this format and faithfully produce the correct aggregations when analyzing the Fact by the Individual Dimension. For example, if you want to sum the Medical Claim amounts for a given Diagnosis, you would select the Diagnosis from the Diagnosis Dimension, drag in your Claim Amount measure, and the semantic software would navigate the Bridge and Group relationship to produce the Total Claim Amount for that one Diagnosis.</p>]]></content:encoded></item><item><title><![CDATA[Slowly Changing Dimension]]></title><description><![CDATA[What exactly are Slowly Changing Dimensions, and why should you care about them?]]></description><link>https://dimodelo.substack.com/p/slowly-changing-dimension</link><guid isPermaLink="false">https://dimodelo.substack.com/p/slowly-changing-dimension</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Wed, 26 Jun 2024 04:55:26 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/1d0c3cc5-419d-4a9e-bb07-19e647020282_702x378.webp" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>What exactly are Slowly Changing Dimensions, and why should you care about them? Many people find themselves asking this question. The term &#8220;Slowly Changing Dimension&#8221; is kind of odd. I mean, aren&#8217;t all Dimensions changing? And why does the speed at which the change matter? Never fear; this article will answer your questions about Slowly Changing Dimensions (SCD), the different <a href="/__u/dimodelo.substack.com/i/160235457/types-of-slowly-changing-dimensions">SCD Types</a> and how to create them. I even provide <a href="/__u/dimodelo.substack.com/i/160235457/the-type-and-scd-dimension-code-pattern">example code</a>, which you can test out for yourself to get a deeper understanding.</p><p>If you need an introduction to Dimension Tables in general, read our <a href="/__u/dimodelo.substack.com/p/dimension-tables-an-introduction/">Dimension Table &#8211; Introduction</a> article.</p><h2>What is a Slowly Changing Dimension?</h2><p>The term &#8220;Slowly Changing Dimension&#8221; (SCD for short) acknowledges that <a href="https://www.dimodelo.com/blog/2024/dimension-tables-an-introduction/">Dimension</a> Members change, but only slowly, over time. However, most Dimensions are, in fact, slowly changing, so why is the concept of &#8220;Slowly Changing Dimensions&#8221; so important in Data Warehousing?</p><p>The <strong>answer </strong>is that there are several different &#8220;Types&#8221; of &#8220;Slowly Changing Dimensions,&#8221; and each one has a different <strong>impact on what data users see in reports</strong> and analyses. Each SCD Type represents a different <strong>change-handling strategy</strong> used to manage changes to Dimension data. Whether users want to report using historical or latest values and how they want to view history dictates the SCD Type you choose to handle changes to Dimension attributes. Therefore, it&#8217;s very important you understand the different types of Slowly Changing Dimensions and their impact when designing a Data Warehouse.</p><p>Where did the concept of &#8220;Slowly Changing Dimensions&#8221; come from? Ralph Kimball originally identified the concept to address the requirement of a Data Warehouse to accurately support historical reporting. He defined the 6 now industry-standard change-handling strategies or &#8220;Types&#8221;. The Types include Types 1, 2, and 3, along with a couple of hybrid techniques, Types 4 and 6.</p><p>Although we talk about Slowly Changing &#8220;Dimensions&#8221;, what we actually implement is <strong>Slowly Changing &#8220;Attributes&#8221;</strong>. <strong>The SCD change-handling strategies are implemented per attribute</strong>. That means different attributes within one Dimension can have different &#8220;Slowly Changing Dimension&#8221; Types. Developers often think of a whole Dimension as being Type 1, 2, etc. That is a mistake. A Dimension can have Type 1, 2, 3 etc attributes at the same time. The ETL patterns we describe in this post show how to handle multiple SCD Types in one Dimension.</p><p>So, to sum up, the term &#8220;Slowly Changing Dimensions&#8221; is kind of confusing. Why is it important to call out the slowly changing nature of Dimensions if almost all Dimensions are slowly changing? The reason is the different ways of handling slowly changing &#8220;attributes&#8221; and the impact they have on reporting.</p><p>The following sections discuss the SCD Types in detail and describe how to write ETL code to implement the SCD Types.</p><h2>Types of Slowly Changing Dimensions</h2><p>People generally agree there are two common SCD Types, 1 and 2, and some less-used SCD types, 3, 4 and 6. The list of Slowly changing dimension types follows:</p><ul><li><p>SCD Type 1 &#8211; Don&#8217;t keep history, i.e. overwrite.</p></li><li><p>SCD Type 2 &#8211; Keep a version of the dimension member for every change.</p></li><li><p>SCD Type 3 &#8211; Keep the latest and prior versions (but not every version).</p></li><li><p>SCD Type 4 &#8211; Current and History Tables.</p></li><li><p>SCD Type 6 &#8211; A hybrid combination of Type 1, 2 and 3.</p></li></ul><p>We use the following example to describe each of the Slowly Changing Dimension Types.</p><p><em>The <a href="/__u/dimodelo.substack.com/p/what-is-a-star-schema-and-why-its-important/">star schema</a> below depicts a typical Sales scenario. Employees sell Products to Customers. The Sales organization is divided into Divisions. Each Sale is a business event and, therefore, can be modelled as a &#8220;Sales&#8221; <a href="/__u/dimodelo.substack.com/p/what-is-a-fact-table-and-why-you-need-them/">Fact</a>. The diagram below depicts the Sales Fact and its related Dimensions. The Dimensions provide the Who (Customer, Employee), the where (Division) and the when (Calendar, Time of Day) context for the Sales Fact.</em></p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!GIr_!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feaf3ed20-82e7-4c37-8de6-ff27d48d86b2_702x378.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!GIr_!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feaf3ed20-82e7-4c37-8de6-ff27d48d86b2_702x378.webp 424w, /__u/substackcdn.com/image/fetch/$s_!GIr_!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feaf3ed20-82e7-4c37-8de6-ff27d48d86b2_702x378.webp 848w, /__u/substackcdn.com/image/fetch/$s_!GIr_!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feaf3ed20-82e7-4c37-8de6-ff27d48d86b2_702x378.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!GIr_!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feaf3ed20-82e7-4c37-8de6-ff27d48d86b2_702x378.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!GIr_!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feaf3ed20-82e7-4c37-8de6-ff27d48d86b2_702x378.webp" width="702" height="378" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/eaf3ed20-82e7-4c37-8de6-ff27d48d86b2_702x378.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:378,&quot;width&quot;:702,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;customer dimension example&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="customer dimension example" title="customer dimension example" srcset="/__u/substackcdn.com/image/fetch/$s_!GIr_!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feaf3ed20-82e7-4c37-8de6-ff27d48d86b2_702x378.webp 424w, /__u/substackcdn.com/image/fetch/$s_!GIr_!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feaf3ed20-82e7-4c37-8de6-ff27d48d86b2_702x378.webp 848w, /__u/substackcdn.com/image/fetch/$s_!GIr_!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feaf3ed20-82e7-4c37-8de6-ff27d48d86b2_702x378.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!GIr_!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Feaf3ed20-82e7-4c37-8de6-ff27d48d86b2_702x378.webp 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Customer Dimension example</figcaption></figure></div><h3>Slowly Changing Dimension Type 1 &#8211; Overwrite</h3><p>The Slowly Changing Dimension (SCD) Type 1 change-handling strategy is used when it doesn&#8217;t make sense to keep an attribute&#8217;s history or when users aren&#8217;t interested in it.</p><p>When an attribute&#8217;s value changes, the SCD Type 1 code simply overwrites the existing value with the new value. Essentially, it records no history of the change.</p><p>Our example has an Employee Dimension associated with a Sales fact. In the Employee Dimension, an Employee Surname is a good example of a Type 1 SCD Attribute. If an Employee&#8217;s Surname changes due to marriage, you want to overwrite the Surname with the new value.</p><p>Since there is only one version of each Employee in the Dimension, all historical Sales Fact records remain associated with the single Employee record, and all future Sales Fact records are associated with the same Employee record.</p><p>Now imagine a report that shows Sales by Employee Name. All Sales are reported against the Employees new name. A desirable outcome.</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!hfnq!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F006aeae6-1991-4dcb-8b01-95abff5c6fd0_243x174.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!hfnq!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F006aeae6-1991-4dcb-8b01-95abff5c6fd0_243x174.png 424w, /__u/substackcdn.com/image/fetch/$s_!hfnq!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F006aeae6-1991-4dcb-8b01-95abff5c6fd0_243x174.png 848w, /__u/substackcdn.com/image/fetch/$s_!hfnq!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F006aeae6-1991-4dcb-8b01-95abff5c6fd0_243x174.png 1272w, /__u/substackcdn.com/image/fetch/$s_!hfnq!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F006aeae6-1991-4dcb-8b01-95abff5c6fd0_243x174.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!hfnq!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F006aeae6-1991-4dcb-8b01-95abff5c6fd0_243x174.png" width="243" height="174" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/006aeae6-1991-4dcb-8b01-95abff5c6fd0_243x174.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:174,&quot;width&quot;:243,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!hfnq!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F006aeae6-1991-4dcb-8b01-95abff5c6fd0_243x174.png 424w, /__u/substackcdn.com/image/fetch/$s_!hfnq!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F006aeae6-1991-4dcb-8b01-95abff5c6fd0_243x174.png 848w, /__u/substackcdn.com/image/fetch/$s_!hfnq!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F006aeae6-1991-4dcb-8b01-95abff5c6fd0_243x174.png 1272w, /__u/substackcdn.com/image/fetch/$s_!hfnq!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F006aeae6-1991-4dcb-8b01-95abff5c6fd0_243x174.png 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a></figure></div><p>If you kept multiple versions of the Employee (e.g., the SCD Type 2 strategy) and looked at the Sales by Employee Name report, the Employee would show up twice, once with the new name and once with the old name. This is an undesirable outcome.</p><p>SCD Type 1 is the most used strategy for handling changes, often serving as developers&#8217; go-to method by default (for better or worse). It&#8217;s also the easiest to implement. Hmmm&#8230;</p><h3>Slowly Changing Dimension Type 2 &#8211; Add a new Version</h3><p>You use the Slowly Changing Dimension Type 2 strategy to ensure that reports present a historically accurate data view. The SCD Type 2 change strategy is designed to keep a history of changes to Type 2 attributes. When a Type 2 attribute value changes, the ETL code pattern I describe later creates a new row. The new row represents a new version of the given Dimension Member. Therefore, there can be more than 1 row for each Dimension Member. In order for reports to present history accurately, The Dimension load pattern must work in tandem with associated <a href="https://www.dimodelo.com/blog/2024/what-is-a-fact-table-and-why-you-need-them/">Fact table</a>&#8216;s load Pattern. I discuss that further later.</p><p>Take the SCD Type 2 example below, which shows a Sales Division Dimension. The example treats the Region attribute as a Type 2 attribute. In the example, The Sales dept decided to move the &#8220;Richmond&#8221; Division from the &#8220;North East&#8221; Region to the &#8220;East Coast&#8221; Region on September the 1st, 2024. As the Region attribute is an SCD Type 2 attribute, this change will result in the creation of a new version row for the &#8220;Richmond&#8221; Division. After September the 1st, 2024, there will be 2 rows in the Dimension for the same &#8220;Richmond&#8221; Division Dimension Member, one with the old Region and one with the new Region.</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!79nE!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F071b72d4-1be9-4ee0-b2bb-5e124a470360_874x144.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!79nE!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F071b72d4-1be9-4ee0-b2bb-5e124a470360_874x144.png 424w, /__u/substackcdn.com/image/fetch/$s_!79nE!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F071b72d4-1be9-4ee0-b2bb-5e124a470360_874x144.png 848w, /__u/substackcdn.com/image/fetch/$s_!79nE!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F071b72d4-1be9-4ee0-b2bb-5e124a470360_874x144.png 1272w, /__u/substackcdn.com/image/fetch/$s_!79nE!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F071b72d4-1be9-4ee0-b2bb-5e124a470360_874x144.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!79nE!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F071b72d4-1be9-4ee0-b2bb-5e124a470360_874x144.png" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/071b72d4-1be9-4ee0-b2bb-5e124a470360_874x144.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:null,&quot;width&quot;:null,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;Slowly changing dimension SCD type 2 example&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="Slowly changing dimension SCD type 2 example" title="Slowly changing dimension SCD type 2 example" srcset="/__u/substackcdn.com/image/fetch/$s_!79nE!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F071b72d4-1be9-4ee0-b2bb-5e124a470360_874x144.png 424w, /__u/substackcdn.com/image/fetch/$s_!79nE!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F071b72d4-1be9-4ee0-b2bb-5e124a470360_874x144.png 848w, /__u/substackcdn.com/image/fetch/$s_!79nE!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F071b72d4-1be9-4ee0-b2bb-5e124a470360_874x144.png 1272w, /__u/substackcdn.com/image/fetch/$s_!79nE!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F071b72d4-1be9-4ee0-b2bb-5e124a470360_874x144.png 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a><figcaption class="image-caption">Example Slowly Changing Dimension Type 2</figcaption></figure></div><p>Note that the system has assigned the new record a new surrogate key (45). Also, note that the system has tagged the new record as the &#8220;latest&#8221; version and set the &#8220;Row Effective Date&#8221; to the date of the change. The system has also set the &#8220;Row End Date&#8221; to the date of the change for the superseded version row ( division skey = 1). The <a href="/__u/dimodelo.substack.com/i/160235457/how-to-create-a-slowly-changing-dimension">How to Create a Slowly Changing Dimension</a> section provides a detailed discussion of this pattern.</p><p>As I mentioned earlier the SCD Type 2 pattern needs to work in tandem with the <a href="https://www.dimodelo.com/blog/2024/what-is-a-fact-table-and-why-you-need-them/">Fact</a> load pattern to accurately present history. To determine which version of the Dimension member to associate with any given Fact, the Fact table load pattern should use a combination of the business key and effective dates. Generally, a Fact will contain some transaction date. The Fact finds the correct Dimension Member version using the business key, where the Fact transaction date is between the Dimensions Effective and End dates.</p><p>Using this logic, all existing Sales Facts prior to September 1st, 2024, remain associated with the original version of the Richmond Division, and all Sales Facts after that date are associated with the new version. If you were to look at a Sales by Region report, Sales prior to September 1st, 2024 appear in the &#8220;North Coast&#8221; Region, and Sales after in the &#8220;East Coast&#8221; Region.</p><h3>Slowly Changing Dimension Type 3 &#8211; Latest and Prior Version</h3><p>With the Slowly Changing Dimension Type 3 change-handling strategy, you only capture the latest and prior values instead of capturing every version of the attribute value, as you do with SCD Type 2. There are some rare circumstances where this is desirable. Take the previous Type 2 SCD example of a Division shifting Regions. What if the business wanted to see today&#8217;s Sales attributed to the new Region but also &#8220;as if&#8221; they had remained in the old Region, just to compare the performance of the old Region to the new one? The SCD Type 2 strategy does not accommodate this kind of request as it never associates new sales with the old Region. A pattern that associates a Fact with both the Old and New Region is necessary, thus the need for the SCD Type 3 pattern.</p><p>SCD type 3 satisfies this comparative kind of reporting requirement. In the SCD Type 3 strategy, you don&#8217;t create a new row for a new version of the Dimension member. Instead, the Dimension contains two columns. One for the current value and one for the prior value of the same attribute.</p><p>For example:</p><p>Revisiting our Richmond Division example, the Richmond Division was in the &#8220;North&#8221; East Region before the change. The Dimension only contained a single column for the Region attribute:</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!R3ov!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F56f6dd10-7403-44db-b417-a59c6342877a_900x96.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!R3ov!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F56f6dd10-7403-44db-b417-a59c6342877a_900x96.webp 424w, /__u/substackcdn.com/image/fetch/$s_!R3ov!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F56f6dd10-7403-44db-b417-a59c6342877a_900x96.webp 848w, /__u/substackcdn.com/image/fetch/$s_!R3ov!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F56f6dd10-7403-44db-b417-a59c6342877a_900x96.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!R3ov!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F56f6dd10-7403-44db-b417-a59c6342877a_900x96.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!R3ov!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F56f6dd10-7403-44db-b417-a59c6342877a_900x96.webp" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/56f6dd10-7403-44db-b417-a59c6342877a_900x96.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:null,&quot;width&quot;:null,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;scd type 3 before&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="scd type 3 before" title="scd type 3 before" srcset="/__u/substackcdn.com/image/fetch/$s_!R3ov!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F56f6dd10-7403-44db-b417-a59c6342877a_900x96.webp 424w, /__u/substackcdn.com/image/fetch/$s_!R3ov!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F56f6dd10-7403-44db-b417-a59c6342877a_900x96.webp 848w, /__u/substackcdn.com/image/fetch/$s_!R3ov!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F56f6dd10-7403-44db-b417-a59c6342877a_900x96.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!R3ov!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F56f6dd10-7403-44db-b417-a59c6342877a_900x96.webp 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a><figcaption class="image-caption">Division Dimension before SCD Type 3 change</figcaption></figure></div><p>To accommodate the Type 3 change, you add a &#8220;prior Region&#8221; column to the table. When the Richmond Division moves to the &#8216;East Coast&#8217; Region, the system transfers the &#8216;North East&#8217; value to the &#8216;prior Region&#8217; column and records &#8216;East Coast&#8217; as the new value in the Region column. See the result below.</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!mQC3!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5c15e462-ce77-46db-ac74-29f9df86a688_964x112.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!mQC3!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5c15e462-ce77-46db-ac74-29f9df86a688_964x112.webp 424w, /__u/substackcdn.com/image/fetch/$s_!mQC3!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5c15e462-ce77-46db-ac74-29f9df86a688_964x112.webp 848w, /__u/substackcdn.com/image/fetch/$s_!mQC3!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5c15e462-ce77-46db-ac74-29f9df86a688_964x112.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!mQC3!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5c15e462-ce77-46db-ac74-29f9df86a688_964x112.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!mQC3!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5c15e462-ce77-46db-ac74-29f9df86a688_964x112.webp" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/5c15e462-ce77-46db-ac74-29f9df86a688_964x112.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:null,&quot;width&quot;:null,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;scd type 3 after&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="scd type 3 after" title="scd type 3 after" srcset="/__u/substackcdn.com/image/fetch/$s_!mQC3!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5c15e462-ce77-46db-ac74-29f9df86a688_964x112.webp 424w, /__u/substackcdn.com/image/fetch/$s_!mQC3!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5c15e462-ce77-46db-ac74-29f9df86a688_964x112.webp 848w, /__u/substackcdn.com/image/fetch/$s_!mQC3!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5c15e462-ce77-46db-ac74-29f9df86a688_964x112.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!mQC3!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5c15e462-ce77-46db-ac74-29f9df86a688_964x112.webp 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a><figcaption class="image-caption">Division Dimension after SCD Type 3 change</figcaption></figure></div><p>Now, the single version of the Dimension member is associated with all Sales Facts, both new and old. Analysts have the option to select the current Region, Prior Region, or both in their reports. This selection enables them to compare sales between the current and prior Regional organizations.</p><p>Note that we don&#8217;t recommend implementing the Type 3 ETL as a separate pattern. Instead, we recommend emulating the Type 3 pattern. Read more about our<a href="/__u/dimodelo.substack.com/i/160235457/slowly-changing-dimensions-recommended-approach"> recommended approach to Slowly Changing Dimensions</a> and implementing <a href="/__u/dimodelo.substack.com/i/160235457/creating-a-scd-type-dimension">SCD Type 3</a>.</p><h3>Slowly Changing Dimension (SCD) Type 4 &#8211; Add a history table</h3><p>Slowly Changing Dimension Type 4 is similar to SCD Type 2, except it stores the historical versions of Dimension Members in a separate table.</p><p>The Dimension is divided into two separate current and history tables. The current table contains only the latest version of each Dimension Member, while the history table contains both the historical and current versions. Both tables share the same surrogate keys.</p><p>SCD Type 4 proves useful when users want to analyze one Fact table that accurately reflects history and another Fact table where history is irrelevant. In such a case, the historical Dimension table is associated with the &#8216;historical&#8217; Fact table, and the &#8216;current&#8217; Fact table uses the current Dimension table.</p><p>SCD Type 4 can also be used to report both a historical and current perspective on the same Fact. In this instance, the Fact is joined to both the Historical and Current Dimensions with 2 separate foreign keys. The outcome is similar to the SCD Type 6 approach below, except there is both a Historical and Current Dimension instead of one Dimension with Historical and Current Attributes.</p><p>I don&#8217;t recommend Type 4. The ETL to manage 2 tables is more difficult, and there are issues in reload scenarios, etc. Instead, I recommend adding a &#8216;latest&#8217; management column to your Type 2 dimensions and using that column when loading Fact tables to associate them with either the historical or current version. See the <a href="/__u/dimodelo.substack.com/i/160235457/implementing-a-type-scd-change-handing-strategy">Implementing SCD Type 4</a> below.</p><h3>Slowly Changing Dimension (SCD) Type 6 Hybrid &#8211; Latest vs Historical Versions</h3><p>The Slowly Changing Dimension Type 6 approach is useful for enabling accurate history reporting while also supporting the ability to report historical data &#8220;as if&#8221; it is attributed to the &#8220;current&#8221; or &#8220;prior&#8221; versions of history.</p><p>Type 6 combines Types 1, 2 and 3 (1+2+3 = 6). It combines the historical versioning described in Type 2 SCD with the Current vs Prior version described in Type 3. To achieve the Type 6 pattern, you add a Type 3 &#8220;prior&#8221; and Type 1 &#8220;current&#8221; attribute to the Dimension. The original attribute contains the Type 2 version of history, and the system updates the &#8220;current&#8221; attribute using a Type 1 SCD change strategy and updates the &#8220;prior&#8221; attribute using a Type 3 change-handling strategy.</p><p>For example, the following images show the Richmond Division, originally belonging to the &#8220;Northeast&#8221; Region. When the Division moves to the &#8220;Mid Coast&#8221;, the system creates a new version of the Richmond Division Dimension Member. The original &#8220;Region&#8221; attribute tracks the Type 2 history of the Region attribute, while the &#8220;Current Region&#8221; tracks the &#8220;Type 1&#8221; latest value of the Region attribute. The &#8220;Prior Region &#8221; attribute tracks the Type 3 prior value of the Region attribute for each version. Again, the process repeats when the Division moves to the &#8220;South Coast&#8221; region.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!R0vl!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F596f81aa-f95f-4c16-9cf7-c6a83f61ac41_1052x450.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!R0vl!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F596f81aa-f95f-4c16-9cf7-c6a83f61ac41_1052x450.webp 424w, /__u/substackcdn.com/image/fetch/$s_!R0vl!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F596f81aa-f95f-4c16-9cf7-c6a83f61ac41_1052x450.webp 848w, /__u/substackcdn.com/image/fetch/$s_!R0vl!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F596f81aa-f95f-4c16-9cf7-c6a83f61ac41_1052x450.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!R0vl!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F596f81aa-f95f-4c16-9cf7-c6a83f61ac41_1052x450.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!R0vl!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F596f81aa-f95f-4c16-9cf7-c6a83f61ac41_1052x450.webp" width="1052" height="450" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/596f81aa-f95f-4c16-9cf7-c6a83f61ac41_1052x450.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:450,&quot;width&quot;:1052,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;SCD Type 6 example&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="SCD Type 6 example" title="SCD Type 6 example" srcset="/__u/substackcdn.com/image/fetch/$s_!R0vl!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F596f81aa-f95f-4c16-9cf7-c6a83f61ac41_1052x450.webp 424w, /__u/substackcdn.com/image/fetch/$s_!R0vl!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F596f81aa-f95f-4c16-9cf7-c6a83f61ac41_1052x450.webp 848w, /__u/substackcdn.com/image/fetch/$s_!R0vl!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F596f81aa-f95f-4c16-9cf7-c6a83f61ac41_1052x450.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!R0vl!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F596f81aa-f95f-4c16-9cf7-c6a83f61ac41_1052x450.webp 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Slowly Changing Dimension Type 6 example.</figcaption></figure></div><p>You can use the &#8220;Region&#8221; attribute to report on sales based on the accurate history of the Division&#8217;s Region. The &#8220;Current Region&#8221; attribute allows you to report on sales based on the latest Region, while the &#8220;Prior Region&#8221; attribute lets you report on sales based on the prior Regional organization.</p><p>Type 6 is powerful and provides analytical options, but users rarely employ it, mainly due to the complexity of data and schema management. Imagine having a Current and Prior attribute for every attribute. You should apply Type 6 selectively, although determining which attributes the business wants to analyze in this way can be challenging up-front. Again, our <a href="/__u/dimodelo.substack.com/i/160235457/slowly-changing-dimensions-recommended-approach">recommended approach</a> suggests emulating <a href="/__u/dimodelo.substack.com/i/160235457/creating-a-scd-type-dimension">Type 6 slowly changing dimensions</a>.</p><h2>How to Create a Slowly Changing Dimension</h2><h3>Slowly Changing Dimensions Recommended Approach</h3><p>Our guiding principles are:</p><ol><li><p><strong>KISS </strong>(Keep it Simple Stupid).</p></li><li><p><strong>Less is More</strong>. Implement as few ETL patterns as possible.</p></li><li><p><strong>Be consistent</strong>. Don&#8217;t do &#8220;special cases&#8221; or skip implementation details for &#8220;simple&#8221; Dimensions.</p></li></ol><p>Our recommended approach is as follows:</p><ol><li><p>Only implement Type 1 and Type 2 SCD in your Dimensions.</p></li><li><p>Stick consistently to a single pattern for all your Dimensions, regardless of whether they contain only Type 1 attributes, only Type 2 attributes, or both. Consistency makes your code simpler to maintain.</p></li><li><p>Less is more. SCD Type 3, 4, and 6 are so rare that it&#8217;s not worth maintaining a different ETL code pattern to load them. Instead, in the rare cases where they are required, you emulate these patterns. For more detail, see the sections on creating Types 3, 4, and 6.</p></li></ol><h3>Slowly Changing Dimension Example</h3><p>I&#8217;ve covered the basics of slowly changing dimensions. To get a better understanding of how to implement the ETL associated with each SCD Type, I&#8217;ll use the following example:</p><p>The <a href="/__u/dimodelo.substack.com/p/what-is-a-star-schema-and-why-its-important/">Star Schema</a> below depicts a typical Sales scenario. Employees sell Products to Customers. The Sales organization is divided into Divisions. Each Sale is a business event and, therefore, can be modelled as a &#8220;Sales&#8221; Fact. The diagram below depicts the Sales Fact and its related Dimensions. The Dimensions provide the who (Customer, Employee), the where (Division) and the when (Calendar, Time of Day) context for the Sales Fact.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!UR6Z!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc11a6592-b259-479e-bb76-74a53cae3825_702x378.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!UR6Z!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc11a6592-b259-479e-bb76-74a53cae3825_702x378.webp 424w, /__u/substackcdn.com/image/fetch/$s_!UR6Z!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc11a6592-b259-479e-bb76-74a53cae3825_702x378.webp 848w, /__u/substackcdn.com/image/fetch/$s_!UR6Z!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc11a6592-b259-479e-bb76-74a53cae3825_702x378.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!UR6Z!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc11a6592-b259-479e-bb76-74a53cae3825_702x378.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!UR6Z!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc11a6592-b259-479e-bb76-74a53cae3825_702x378.webp" width="702" height="378" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/c11a6592-b259-479e-bb76-74a53cae3825_702x378.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:378,&quot;width&quot;:702,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;customer dimension example&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="customer dimension example" title="customer dimension example" srcset="/__u/substackcdn.com/image/fetch/$s_!UR6Z!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc11a6592-b259-479e-bb76-74a53cae3825_702x378.webp 424w, /__u/substackcdn.com/image/fetch/$s_!UR6Z!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc11a6592-b259-479e-bb76-74a53cae3825_702x378.webp 848w, /__u/substackcdn.com/image/fetch/$s_!UR6Z!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc11a6592-b259-479e-bb76-74a53cae3825_702x378.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!UR6Z!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc11a6592-b259-479e-bb76-74a53cae3825_702x378.webp 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Customer Dimension example</figcaption></figure></div><p>Our example will focus on the <strong>Customer </strong>Dimension. The following sections outline the modelling and ETL patterns you need to create and manage this Dimension.</p><h3>A Universal Data Model for Dimensions</h3><p>As discussed previously, you should only implement Type 1 and 2 Slowly Changing Dimension change strategies in your Dimensions (and emulate Type 3,4 and 6). Sticking to our <a href="#slowly-changing-dimensions-recommended-approach">principles</a>, we want to define a consistent data model for all our Dimensions regardless of whether they contain only Type 1 attributes, only Type 2 attributes, or both. You never know when a requirement might emerge to change an attribute from Type 1 to Type 2 or vice versa.</p><p>As discussed in &#8220;<a href="/__u/dimodelo.substack.com/p/dimension-tables-an-introduction/">Introduction to Dimensions</a>&#8220;, I showed the following example of the Customer Dimension:</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!y5EJ!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbdd9cfd0-1fdc-414f-8bad-4ebd8633577c_360x652.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!y5EJ!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbdd9cfd0-1fdc-414f-8bad-4ebd8633577c_360x652.webp 424w, /__u/substackcdn.com/image/fetch/$s_!y5EJ!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbdd9cfd0-1fdc-414f-8bad-4ebd8633577c_360x652.webp 848w, /__u/substackcdn.com/image/fetch/$s_!y5EJ!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbdd9cfd0-1fdc-414f-8bad-4ebd8633577c_360x652.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!y5EJ!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbdd9cfd0-1fdc-414f-8bad-4ebd8633577c_360x652.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!y5EJ!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbdd9cfd0-1fdc-414f-8bad-4ebd8633577c_360x652.webp" width="360" height="652" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/bdd9cfd0-1fdc-414f-8bad-4ebd8633577c_360x652.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:652,&quot;width&quot;:360,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!y5EJ!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbdd9cfd0-1fdc-414f-8bad-4ebd8633577c_360x652.webp 424w, /__u/substackcdn.com/image/fetch/$s_!y5EJ!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbdd9cfd0-1fdc-414f-8bad-4ebd8633577c_360x652.webp 848w, /__u/substackcdn.com/image/fetch/$s_!y5EJ!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbdd9cfd0-1fdc-414f-8bad-4ebd8633577c_360x652.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!y5EJ!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbdd9cfd0-1fdc-414f-8bad-4ebd8633577c_360x652.webp 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Customer Dimension Design</figcaption></figure></div><p>The &#8220;<a href="/__u/dimodelo.substack.com/p/dimension-tables-an-introduction/">Introduction to Dimensions</a>&#8221; article describes the various types of columns in a Dimension. For the purposes of this exercise, we are mostly interested in the &#8220;row management columns.&#8221; The Dimension ETL patterns use these columns to manage appropriate Inserts and Updates, speed up ETL execution, and facilitate change logging and auditing.</p><p>The Row Management Columns are as follows:</p><ul><li><p><strong>row_is_latest</strong>. Indicates the row version is the latest row version, 0 = row is a superceded version.</p></li><li><p><strong>row_is_deleted</strong>. Indicates that the source system has deleted a row with the same business key.</p></li><li><p><strong>row_effective_date</strong>. The start date and time (to the microsecond) that the row version becomes effective. For the first row version, row_effective_date is &#8220;low date&#8221; (i.e. 0001-01-01&#8230;). Fact table ETL patterns require Dimensions to have effective dates to associate Facts with the correct version of Dimension Members accurately.</p></li><li><p><strong>row_end_date</strong>. The end date and time (to the microsecond) that the row version becomes no longer effective. This is always the effective date of the next row version in the series of row versions. Therefore, row versions&#8217; effective date and end dates are contiguous. For the last row version, row_end_date is &#8220;high date&#8221; (9999-12-31&#8230;.). The BETWEEN SQL clause can&#8217;t be used to join across row effective and end dates. Instead, use a clause similar to this: X &gt;= Row_Effective_Date and X &lt; Row_End_Date, where X is the transaction date of the Fact.</p></li><li><p><strong>row_inserted_batch_id</strong>. The system creates a new batch ID for every batch execution and sets the row_inserted_batch_id to the ID of the batch that inserted the row.</p></li><li><p><strong>row_updated_batch_id</strong>. The system sets the row_upaated_batch_id to the last batch Id that updated the row.</p></li><li><p><strong>row_scd_type_1_hash</strong>. A hash of all SCD Type 1 attribute values. Used by the ETL to compare incoming rows to detect any Type 1 changes.</p></li><li><p><strong>row_scd_type_2_hash</strong>. A hash of all SCD Type 2 attribute values. Used by the ETL to compare incoming rows to detect any Type 2 changes.</p></li><li><p><strong>row_supercedes_skey</strong> Optional. Records the surrogate key of the row that this row has superseded due to a Type 2 change. Used to speed up ETL execution and provides a convenient method of viewing and auditing the history for any given Dimension Member. Since Dimensions are generally relatively small, there is no harm in including this column.</p></li><li><p><strong>row_last_tran_code</strong> Optional. A useful indicator that helps debugging and audit exercises. Since Dimensions are generally relatively small, there is no harm in including this column.</p></li></ul><p>This seems like a lot of columns, but each has its purpose. Dimensions are generally small, so the increase in storage is negligible. I, therefore, would argue to keep all columns. However, there are options to reduce the number of columns:</p><ul><li><p>The row_supercedes_skey and row_last_tran_code are optional. Depending on how you manage ETL runs, the batch_id columns may not be needed.</p></li><li><p>The row_is_latest and row_is_deleted are bit data types, meaning they occupy one bit of a shared byte on the record. This leaves room for 6 additional bit fields that don&#8217;t occupy any additional space. You could potentially use 2 bits for the <em>row_last_tran_code</em>, but all you save is one byte per row.</p></li><li><p>The largest columns are <em>row_scd_type_1_hash</em> and <em>row_scd_type_2_hash</em>, at 20 bytes each. You could recalculate them each time the ETL runs instead of storing them. However, this means additional coding and processing overhead. I opt to store them to make the ETL simpler and faster.</p></li></ul><h3>The Type 1 and 2 SCD Dimension Code Pattern</h3><p>The following code implements the Type 1 and 2 SCD ETL code pattern for the example Customer Dimension. The Customer Dimension contains a mix of SCD Type 1 and 2 attributes:</p><ul><li><p>The Type 1 attributes include name, language and employer.</p></li><li><p>The Type 2 attributes include language, type, income_level, marital_status and credit_profile.</p></li></ul><p>The SQL code, originally written for a PostgreSQL database, can be easily modified to run on various platforms such as Snowflake, Databricks, Microsoft Fabric, Google Big Query, or AWS Redshift. The great thing about SQL is that it is ubiquitous across platforms, although each platform has slightly different SQL dialects.</p><p>SQL uses a series of chained common table expressions (CTE). CTEs are temporary named result data sets that only exist during the execution of a single query. They act like virtual tables that can be referenced later in other CTEs or the main query.</p><p>The advantages of this approach are:</p><ol><li><p>CTEs (Common Table Expressions) generate temporary results, such as the <em>delta </em>result set below, which the system evaluates only once. However, these results can serve multiple subsequent queries, thereby enhancing performance.</p></li><li><p>PostgreSQL (and some other SQL dialects) can include INSERT, UPDATE and DELETE statements in CTEs.</p></li><li><p>PostgreSQL also has a feature where INSERTs, UPDATEs, and DELETEs can output a result set of updated rows. This can improve performance, as the result of one update may serve as the input for another, such as the type_2_supercede CTE shown in the following code.</p></li><li><p>You can use this single, self-contained script as a pattern for all your Dimensions.</p></li></ol><p>Below is the code consisting of the following 5 chained CTEs and a final query:</p><ol><li><p><strong>Source CTE</strong>. Composes the source data.</p></li><li><p><strong>Delta CTE</strong>. Determines the delta change set.</p></li><li><p><strong>Inserts CTE</strong>. Insert the New and Type 2 change records. Returns a list of surrogate keys of superceded type 2 rows.</p></li><li><p><strong>Type_2_supercede CTE</strong>. This CTE updates rows superseded by new Type 2 versions.</p></li><li><p><strong>Type_1_update CTE</strong>. Applies Type 1 changes.</p></li><li><p><strong>Soft delete final query</strong>. A &#8220;soft&#8221; delete of any rows no longer present in the source.</p></li></ol><p>The SQL is explained further following the script.</p><pre><code>/*************************************************************************
DIMODELO.COM

Type 1 and 2 Dimension ETL pattern

**************************************************************************/

CREATE OR REPLACE PROCEDURE dim_customer_type_1_and_2_update(batch integer)
LANGUAGE SQL
AS $$

-- compose the "source"
WITH "source" AS (
    SELECT customer_id, "name", "language", "type", employer, income_level, marital_status, credit_profile,
    digest("type" || ',' || income_level || ',' || marital_status || ',' || credit_profile ,'sha1') as row_scd_type_2_hash,
    digest(name || ',' || language || ',' || employer ,'sha1') as row_scd_type_1_hash
    FROM stg.customers
),

-- derive delta change set
delta AS (
    SELECT "source".*, dim.skey as dim_skey,
    CASE    WHEN (dim.customer_id = "source".customer_id) AND dim.row_scd_type_2_hash != "source".row_scd_type_2_hash THEN '2' -- type 2 change
            WHEN (dim.customer_id = "source".customer_id) AND dim.row_scd_type_1_hash !=  "source".row_scd_type_1_hash THEN '1' -- type 1 change
            WHEN dim.customer_id is NULL THEN 'N' --new
            WHEN "source".customer_id is NULL THEN 'D' --deleted
            ELSE 'unknown' END AS tran_type
    FROM "source"
    FULL OUTER JOIN whs.dim_customer dim
    ON dim.customer_id = "source".customer_id AND dim.row_is_latest = CAST(1 AS BIT)
    WHERE (dim.customer_id = "source".customer_id) AND dim.row_scd_type_2_hash !=  "source".row_scd_type_2_hash -- type 2 changes condition
    OR (dim.customer_id = "source".customer_id) AND dim.row_scd_type_1_hash !=  "source".row_scd_type_1_hash -- type 1 changes condition
    OR dim.customer_id is NULL -- new records condition
    OR (dim.row_is_latest = CAST(1 AS BIT) AND "source".customer_id is NULL) -- deleted records condition
),

-- insert new and type 2 records
inserts as (
    INSERT INTO whs.dim_customer  (customer_id, "name", "language", "type", employer, income_level, marital_status, 
          credit_profile, row_is_latest, row_is_deleted, row_effective_date, row_end_date,
          row_inserted_batch_id, row_updated_batch_id, row_scd_type_1_hash, row_scd_type_2_hash,row_supercedes_skey,
          row_last_tran_code)
    SELECT  customer_id, "name", "language", "type", employer, income_level, marital_status,
            credit_profile, CAST(1 AS bit), CAST(0 AS BIT), 
            CASE WHEN dim_skey IS NOT NULL THEN CURRENT_TIMESTAMP(6) ELSE '0001-01-01' END,
            '31-12-9999',
            batch, NULL, row_scd_type_1_hash,row_scd_type_2_hash, dim_skey,
            tran_type
    FROM delta
    WHERE delta.tran_type in ('2', 'N')
    RETURNING row_supercedes_skey
),

-- update superceded records (by type 2 changes)
type_2_supercede as (
UPDATE whs.dim_customer AS dim
SET row_end_date = CURRENT_TIMESTAMP(6),
    row_is_latest = CAST(0 AS BIT),
    row_updated_batch_id = batch,
    row_last_tran_code = 'S'
FROM inserts
WHERE dim.skey = inserts.row_supercedes_skey
),

-- update records with type 1 changes
type_1_update as (
UPDATE whs.dim_customer AS dim
SET     "name" = delta."name",
        "language" = delta."language",
        employer = delta.employer,
        row_updated_batch_id = batch, 
        row_scd_type_1_hash = delta.row_scd_type_1_hash,
        row_last_tran_code = tran_type
FROM delta
WHERE delta.tran_type = '1'
AND dim.customer_id = delta.customer_id
)

-- finally soft deletes
UPDATE whs.dim_customer AS dim
SET     row_updated_batch_id = batch,
        row_end_date = CURRENT_TIMESTAMP(6),
        row_is_deleted = CAST(1 AS bit),
        row_last_tran_code = tran_type
FROM delta
WHERE dim.skey = delta.dim_skey
AND delta.tran_type = 'D'
;

$$;</code></pre><h3>Type 1 and 2 ETL Pattern Explained</h3><p>The following diagram and dot points break down and describe the code in detail:</p><ul><li><p><strong>Staging Sources</strong>. This pattern assumes that we have loaded the source data into accessible staging tables, following the standard data warehouse architecture. The staging source is either a periodic full copy of source tables/data or a persistent copy of staging data that replicates the source.</p></li><li><p><strong>Compose Source</strong> <strong>(source CTE)</strong>: The Data source of a Dimension could be a complex join across a set of source staging tables. This step composes the source from its source staging tables, selects values for all the Dimension attributes, and calculates the <strong>row_scd_type_1_hash</strong> and <strong>row_scd_type_2_hash</strong> Hashes for the source rows. The code concatenates and hashes Type 1 identified columns into the row_scd_type_1_hash, and similarly, it concatenates and hashes Type 2 identified columns into the row_scd_type_2_hash. The Hashes use the SHA-1 (<a href="https://en.wikipedia.org/wiki/SHA-1">SHA1 &#8211; Wikipedia</a>) hashing algorithm. The SHA-1 algorithm remains suitable for &#8220;comparison&#8221; purposes, although it is no longer deemed secure for encryption. It generates a relatively compact hash value that is adequately free of collisions and enjoys broad support across databases. MD5 is not advised due to its high rate of collisions, while SHA-256 and higher algorithms yield hash values that are 50% larger.</p></li><li><p><strong>&#8220;source&#8221;</strong>. The temporary result of the &#8220;Compose Source&#8221; step.</p></li></ul><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!rY2L!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb8f288e1-b27d-47ba-9c9a-2007e6ea3a02_335x902.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!rY2L!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb8f288e1-b27d-47ba-9c9a-2007e6ea3a02_335x902.webp 424w, /__u/substackcdn.com/image/fetch/$s_!rY2L!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb8f288e1-b27d-47ba-9c9a-2007e6ea3a02_335x902.webp 848w, /__u/substackcdn.com/image/fetch/$s_!rY2L!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb8f288e1-b27d-47ba-9c9a-2007e6ea3a02_335x902.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!rY2L!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb8f288e1-b27d-47ba-9c9a-2007e6ea3a02_335x902.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!rY2L!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb8f288e1-b27d-47ba-9c9a-2007e6ea3a02_335x902.webp" width="335" height="902" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/b8f288e1-b27d-47ba-9c9a-2007e6ea3a02_335x902.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:902,&quot;width&quot;:335,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!rY2L!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb8f288e1-b27d-47ba-9c9a-2007e6ea3a02_335x902.webp 424w, /__u/substackcdn.com/image/fetch/$s_!rY2L!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb8f288e1-b27d-47ba-9c9a-2007e6ea3a02_335x902.webp 848w, /__u/substackcdn.com/image/fetch/$s_!rY2L!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb8f288e1-b27d-47ba-9c9a-2007e6ea3a02_335x902.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!rY2L!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fb8f288e1-b27d-47ba-9c9a-2007e6ea3a02_335x902.webp 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Slowly Changing Dimension Type 1 and 2 ETL Pattern</figcaption></figure></div><ul><li><p><strong>Derive delta change set</strong>. In this step, the process derives a data set of the records that have changed in the source when compared to the Dimension.</p><ul><li><p>First, the source is joined to the Dimension on the business key of the Dimension (in this case, customer_id)using a <strong>FULL OUTER JOIN</strong>. A Full Outer Join is necessary to identify deletes. FULL OUTER JOINs can be expensive, but Dimensions are generally small, so performance is rarely an issue. If a full outer join wasn&#8217;t used, you need a second separate query. Weighing these two facts, it&#8217;s better to do a single Full Outer Join.</p></li><li><p>The <strong>WHERE</strong> clause selects rows where a matching row (based on the business key) exists in both the source and Dimension, and the Source and Dimension Hashes are different, indicating a Type 1 or 2 change. It also identifies new records (i.e., in the Source but not in the Dimension) and deleted records (i.e., in the Dimension but not in the Source).</p></li><li><p>The query derives a <strong>tran_type</strong> column to indicate the detected change type. The query sets the tran_type to &#8220;1&#8221; for a Type 1 change, to &#8220;2&#8221; for a Type 2 change, to &#8220;N&#8221; for a new record, or to &#8220;D&#8221; if the record is deleted.</p></li><li><p>The query <strong>SELECT</strong>s everything in the source table plus the surrogate key of the matching Dimension row (if there is one). The &#8220;Supercede Old Type 2 Records&#8221; step uses the surrogate key later.</p></li></ul></li><li><p><strong>&#8220;delta&#8221;</strong>. The &#8220;Derive Changes&#8221; step outputs the temporary <strong>delta</strong> change data set. Subsequent Update statements use the &#8220;delta&#8221; data set multiple times. Creating a &#8220;delta&#8221; dataset has the advantage of a one-time initialization, repeated utilization, and operation with a significantly smaller dataset. This smaller dataset can be easily filtered by transaction type in subsequent updates, thus improving performance.</p></li><li><p><strong>Insert New and Type 2 Records</strong>. The &#8220;Insert New Records&#8221; inserts new Dimension Members that don&#8217;t already exist, along with new versions of any Dimension Members subject to an SCD Type 2 change. I.e. delta record with <strong>tran_type</strong> equal to 2 or N. The <strong>RETURNING </strong>clause returns a set of rows that contain the surrogate keys of the rows that were superseded by new Insertions.</p></li><li><p><strong>Updated Superceded Records</strong>. Updates the previous &#8220;latest&#8221; version of the Dimension Member, which the new version has superseded, to set its row_effective_end_date and row_is_latest flag. The previous &#8220;Insert New Record&#8221; step outputs a list of surrogate keys of superseded rows. This Update statement updates every row in that list, setting its row_effective_end_date and row_is_latest flag.</p></li><li><p><strong>Update Records with Type 1 Changes</strong>. The Type 1 Update statement updates any record when it identifies a type 1 change (tran_type = 1). It updates all records in the Dimension that match any business key of rows in &#8220;delta&#8221; where a tran_type =1. You update all versions of the matching Dimension Member (based on the business key).</p></li><li><p><strong>Soft Deletes</strong>. Finally, the query &#8220;soft&#8221; deletes any records in the Dimension corresponding to deleted rows in the source. A soft delete sets the row_is_deleted flag and <strong>row_end_date </strong>of the Dimension row rather than deleting the row from the Dimension. You only &#8220;soft&#8221; delete data because historical Facts in Fact tables may still reference the deleted Dimension member.</p></li></ul><h3>Creating a SCD Type 3 Dimension</h3><p>As discussed, the SCD Type 3 change-handling strategy only captures the latest and prior value of an attribute in separate columns.</p><p>In our <a href="/__u/dimodelo.substack.com/i/160235457/slowly-changing-dimensions-recommended-approach">recommended approach</a> we suggested only implementing Type 1 and 2 SCD ETL patterns and to emulate SCD Type 3. Developers use the Type 3 Slowly Changing Dimension (SCD) pattern very rarely, and investing in a specific pattern is not worthwhile when simple emulation is possible. To emulate Type 3 SCD, first the attribute must be a Type 2 attribute. If it&#8217;s not, then change it, then create a view similar to this example:</p><p>In our example we want to show the latest and prior values of the credit_profile attribute of the Customer Dimension. Use the SQL <em>lag </em>windows function. The query is as simple as this:</p><pre><code>CREATE OR REPLACE VIEW whs.dim_customer_type_3
AS
SELECT * FROM
(
    SELECT *,
    LAG(credit_profile,1,NULL) OVER(PARTITION BY customer_id ORDER BY skey) 
    AS prior_credit_profile
FROM whs.dim_customer) S
WHERE row_is_latest = CAST(1 AS BIT);</code></pre><p>The output looks like this:</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!mmL-!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc12a38b5-1afc-440b-ac59-6e2c8149db5d_1070x93.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!mmL-!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc12a38b5-1afc-440b-ac59-6e2c8149db5d_1070x93.webp 424w, /__u/substackcdn.com/image/fetch/$s_!mmL-!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc12a38b5-1afc-440b-ac59-6e2c8149db5d_1070x93.webp 848w, /__u/substackcdn.com/image/fetch/$s_!mmL-!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc12a38b5-1afc-440b-ac59-6e2c8149db5d_1070x93.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!mmL-!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc12a38b5-1afc-440b-ac59-6e2c8149db5d_1070x93.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!mmL-!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc12a38b5-1afc-440b-ac59-6e2c8149db5d_1070x93.webp" width="1070" height="93" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/c12a38b5-1afc-440b-ac59-6e2c8149db5d_1070x93.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:93,&quot;width&quot;:1070,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!mmL-!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc12a38b5-1afc-440b-ac59-6e2c8149db5d_1070x93.webp 424w, /__u/substackcdn.com/image/fetch/$s_!mmL-!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc12a38b5-1afc-440b-ac59-6e2c8149db5d_1070x93.webp 848w, /__u/substackcdn.com/image/fetch/$s_!mmL-!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc12a38b5-1afc-440b-ac59-6e2c8149db5d_1070x93.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!mmL-!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc12a38b5-1afc-440b-ac59-6e2c8149db5d_1070x93.webp 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a></figure></div><h3>Implementing a Type 4 SCD change-handing strategy</h3><p>SCD Type 4 is similar to SCD Type 2, except you keep the historical versions of Dimension Members in a separate table. You divide the Dimension into a current table and a history table.</p><p>In our <a href="#slowly-changing-dimensions-recommended-approach">recommended approach</a>, we suggested only implementing Type 1 and 2 SCD and instead emulating SCD Type 4. Developers use the Type 4 Slowly Changing Dimension (SCD) pattern very rarely, and investing in a specific pattern is not worthwhile when simple emulation is possible. In fact, we recommend never using Type 4. However, to emulate Type 4 SCD, create a view representing the &#8220;current&#8221; table, similar to this example:</p><pre><code>CREATE OR REPLACE VIEW whs.dim_customer_current
AS
SELECT *
FROM whs.dim_customer
WHERE row_is_latest = CAST(1 AS BIT);</code></pre><p>The existing table represents the historical table.</p><h3>Creating a SCD Type 6 Dimension</h3><p>The Type 6 approach is beneficial for reporting historical data accurately and simultaneously allowing the data to be presented as if it were attributed to the current version of history.</p><p>Type 6 is a combination of types 1, 2, and 3 (1+2+3 = 6). It combines the historical versioning described in Type 2 SCD with the Current vs. Prior version described in Type 3.</p><p>In our <a href="/__u/dimodelo.substack.com/i/160235457/slowly-changing-dimensions-recommended-approach">recommended approach</a>, we suggested only implementing Type 1 and 2 SCD and just emulating SCD Type 6. Developers use the Type 6 Slowly Changing Dimension (SCD) pattern very rarely, and investing in a specific pattern is not worthwhile when simple emulation is possible. To emulate Type 6 SCD, first, the attribute must be a Type 2 attribute. If it&#8217;s not, then change it, then create a view similar to this example:</p><p>In our example, we want to show the current, prior and historical values of the credit_profile attribute of the Customer Dimension. You can achieve this with an SQL <strong>LAG</strong> Window function and a <strong>JOIN</strong> to the &#8220;latest&#8221; version of each Dimension Member. The query is as simple as this:</p><pre><code>CREATE OR REPLACE VIEW whs.dim_customer_type_6
AS
SELECT prior.*, cur.current_credit_profile,
LAG(credit_profile,1,NULL) OVER(PARTITION BY customer_id ORDER BY skey) 
AS prior_credit_profile
FROM whs.dim_customer "prior"
JOIN (
    SELECT customer_id AS current_customer_id, 
    credit_profile AS current_credit_profile
    FROM whs.dim_customer
    WHERE row_is_latest = CAST(1 AS BIT)    
) cur
ON prior.customer_id = cur.current_customer_id</code></pre><p>The output looks like this:</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!WBNg!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff0096e22-a12f-4142-b8a1-f2bbaed6dda3_1227x110.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!WBNg!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff0096e22-a12f-4142-b8a1-f2bbaed6dda3_1227x110.webp 424w, /__u/substackcdn.com/image/fetch/$s_!WBNg!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff0096e22-a12f-4142-b8a1-f2bbaed6dda3_1227x110.webp 848w, /__u/substackcdn.com/image/fetch/$s_!WBNg!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff0096e22-a12f-4142-b8a1-f2bbaed6dda3_1227x110.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!WBNg!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff0096e22-a12f-4142-b8a1-f2bbaed6dda3_1227x110.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!WBNg!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff0096e22-a12f-4142-b8a1-f2bbaed6dda3_1227x110.webp" width="1227" height="110" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/f0096e22-a12f-4142-b8a1-f2bbaed6dda3_1227x110.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:110,&quot;width&quot;:1227,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!WBNg!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff0096e22-a12f-4142-b8a1-f2bbaed6dda3_1227x110.webp 424w, /__u/substackcdn.com/image/fetch/$s_!WBNg!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff0096e22-a12f-4142-b8a1-f2bbaed6dda3_1227x110.webp 848w, /__u/substackcdn.com/image/fetch/$s_!WBNg!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff0096e22-a12f-4142-b8a1-f2bbaed6dda3_1227x110.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!WBNg!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff0096e22-a12f-4142-b8a1-f2bbaed6dda3_1227x110.webp 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a></figure></div>]]></content:encoded></item><item><title><![CDATA[Dimension Tables – An Introduction]]></title><description><![CDATA[A Dimension table is one of the 3 key elements of dimensional modelling used to build a Data Warehouse. This article will give you an in-depth understanding of various Dimension table concepts.]]></description><link>https://dimodelo.substack.com/p/dimension-tables-an-introduction</link><guid isPermaLink="false">https://dimodelo.substack.com/p/dimension-tables-an-introduction</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Fri, 03 May 2024 10:44:14 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/129e837b-d959-4c5b-8c4a-749d9e44bc39_702x378.webp" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>A <strong>Dimension table</strong> is one of the 3 key elements of <a href="/__u/dimodelo.substack.com/p/what-is-dimensional-modeling-introduction/">dimensional modelling</a> used to build a <a href="/__u/dimodelo.substack.com/p/what-is-a-data-warehouse-and-why-you-need-one/">Data Warehouse</a>. This article will give you an in-depth understanding of various Dimension table concepts.</p><h2>What is a Dimension Table?</h2><p>Conceptually, Dimension tables are database tables modelled to represent the business entities involved in business processes and events. The business processes are, in turn, modelled as <a href="/__u/dimodelo.substack.com/p/what-is-a-fact-table-and-why-you-need-them/">Fact tables</a>, and the Fact and Dimension tables are related in a &#8220;<a href="/__u/dimodelo.substack.com/p/what-is-a-star-schema-and-why-its-important/">Star Schema</a>&#8221; to provide an easy-to-navigate and query Data Warehouse database.</p><p>Where Fact tables represent the &#8220;numbers&#8221; you want to analyze, Dimension Tables provide the context by which you analyze those numbers. The Who, What, Where, When and Why.</p><p>For example, imagine a typical Sales scenario. Employees sell Products to Customers. The Sales organization is divided into Divisions. Each Sale is a business event and, therefore, can be modelled as a &#8220;Sales&#8221; Fact. The diagram below depicts the Sales Fact and its related Dimensions. The Dimensions provide the Who (Customer, Employee), the where (Division) and the when (Calendar, Time of Day) context for the Sales Fact.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!V-8_!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3b3abb07-bdf7-4ad5-81f2-d57a31221476_702x378.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!V-8_!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3b3abb07-bdf7-4ad5-81f2-d57a31221476_702x378.webp 424w, /__u/substackcdn.com/image/fetch/$s_!V-8_!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3b3abb07-bdf7-4ad5-81f2-d57a31221476_702x378.webp 848w, /__u/substackcdn.com/image/fetch/$s_!V-8_!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3b3abb07-bdf7-4ad5-81f2-d57a31221476_702x378.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!V-8_!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3b3abb07-bdf7-4ad5-81f2-d57a31221476_702x378.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!V-8_!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3b3abb07-bdf7-4ad5-81f2-d57a31221476_702x378.webp" width="702" height="378" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/3b3abb07-bdf7-4ad5-81f2-d57a31221476_702x378.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:378,&quot;width&quot;:702,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;sales fact customer dimension table star schema&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="sales fact customer dimension table star schema" title="sales fact customer dimension table star schema" srcset="/__u/substackcdn.com/image/fetch/$s_!V-8_!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3b3abb07-bdf7-4ad5-81f2-d57a31221476_702x378.webp 424w, /__u/substackcdn.com/image/fetch/$s_!V-8_!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3b3abb07-bdf7-4ad5-81f2-d57a31221476_702x378.webp 848w, /__u/substackcdn.com/image/fetch/$s_!V-8_!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3b3abb07-bdf7-4ad5-81f2-d57a31221476_702x378.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!V-8_!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3b3abb07-bdf7-4ad5-81f2-d57a31221476_702x378.webp 1456w" sizes="100vw" fetchpriority="high"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Sales Fact Star Schema</figcaption></figure></div><p>Dimension tables physically contain the descriptive attributes of the business entities. For example, a Customer Dimension would contain attributes like Customer Name, Age, and Gender. The attributes filter and group the Fact table data in reports and analysis. See the next section for more details.</p><h2>How to Design a Dimension Table</h2><p>A Dimension contains&nbsp;<strong>Members</strong>. There is a Member for every&nbsp;<strong>business/natural key</strong>&nbsp;of the Dimension. For example, in a Customer dimension, there is one member for each individual Customer. However, because a Dimension may keep the history of change for each member, there may be multiple rows in the Dimension table for each member, one for each version. To handle this, Kimball introduced the concept of a <a href="#Dimension-Surrogate-Key-vs-Business-Key">surrogate key</a>.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!F7sw!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fcbd45f78-458f-46ba-bd25-b7a3097cbc96_374x566.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!F7sw!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fcbd45f78-458f-46ba-bd25-b7a3097cbc96_374x566.webp 424w, /__u/substackcdn.com/image/fetch/$s_!F7sw!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fcbd45f78-458f-46ba-bd25-b7a3097cbc96_374x566.webp 848w, /__u/substackcdn.com/image/fetch/$s_!F7sw!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fcbd45f78-458f-46ba-bd25-b7a3097cbc96_374x566.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!F7sw!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fcbd45f78-458f-46ba-bd25-b7a3097cbc96_374x566.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!F7sw!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fcbd45f78-458f-46ba-bd25-b7a3097cbc96_374x566.webp" width="374" height="566" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/cbd45f78-458f-46ba-bd25-b7a3097cbc96_374x566.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:566,&quot;width&quot;:374,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;dimension table schema&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="dimension table schema" title="dimension table schema" srcset="/__u/substackcdn.com/image/fetch/$s_!F7sw!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fcbd45f78-458f-46ba-bd25-b7a3097cbc96_374x566.webp 424w, /__u/substackcdn.com/image/fetch/$s_!F7sw!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fcbd45f78-458f-46ba-bd25-b7a3097cbc96_374x566.webp 848w, /__u/substackcdn.com/image/fetch/$s_!F7sw!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fcbd45f78-458f-46ba-bd25-b7a3097cbc96_374x566.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!F7sw!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fcbd45f78-458f-46ba-bd25-b7a3097cbc96_374x566.webp 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Dimension Table Schema</figcaption></figure></div><h3>Dimension Surrogate Key vs Business Key</h3><p>Because a Dimension can keep multiple rows for different versions of any Member, the business key of a Member can be duplicated over multiple rows. Therefore, the business key can&#8217;t be used as the unique primary key. Instead, each row is assigned a unique&nbsp;<strong>surrogate key</strong>&nbsp;by the data warehouse. The surrogate key becomes the&nbsp;<strong>primary/unique key</strong>&nbsp;of the Dimension. Usually, a surrogate key is a sequentially assigned integer. In recent years generating a hash on the business key and effective date combination has become popular. There are cases where you may want to use a&nbsp;<strong>&#8220;smart&#8221; surrogate key</strong>. I.e. a code for the surrogate key. A typical example is the Calendar Dimension, with a smart key like &#8220;YYYYMMDD&#8221; used as the surrogate key for each row (representing a day) in the Calendar. Read <a href="https://www.dimodelo.com/defining-dimension-smart-keys/">more about Smart Keys</a>.</p><p>Note that a surrogate key is only strictly needed for Dimension Tables, which contain type 2 (version history) attributes. However, I recommend assigning a surrogate key to every Dimension for uniformity and future-proofing.</p><h3>Dimension Table Attributes</h3><p>Attributes are the columns of Dimensions that contain descriptive information for each Member. E.g. Customer Name, Customer Income Level, Marital Status etc.</p><p>It&#8217;s important to understand that attribute values (not the attribute column names) become row and column headers in pivot tables/charts. For example, a pivot table showing sales by gender in the past 12 months would look something like this:</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!9s1L!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F39dab6b0-b957-4f04-949d-d6a777a5de30_306x326.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!9s1L!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F39dab6b0-b957-4f04-949d-d6a777a5de30_306x326.png 424w, /__u/substackcdn.com/image/fetch/$s_!9s1L!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F39dab6b0-b957-4f04-949d-d6a777a5de30_306x326.png 848w, /__u/substackcdn.com/image/fetch/$s_!9s1L!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F39dab6b0-b957-4f04-949d-d6a777a5de30_306x326.png 1272w, /__u/substackcdn.com/image/fetch/$s_!9s1L!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F39dab6b0-b957-4f04-949d-d6a777a5de30_306x326.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!9s1L!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F39dab6b0-b957-4f04-949d-d6a777a5de30_306x326.png" width="306" height="326" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/39dab6b0-b957-4f04-949d-d6a777a5de30_306x326.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:326,&quot;width&quot;:306,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!9s1L!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F39dab6b0-b957-4f04-949d-d6a777a5de30_306x326.png 424w, /__u/substackcdn.com/image/fetch/$s_!9s1L!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F39dab6b0-b957-4f04-949d-d6a777a5de30_306x326.png 848w, /__u/substackcdn.com/image/fetch/$s_!9s1L!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F39dab6b0-b957-4f04-949d-d6a777a5de30_306x326.png 1272w, /__u/substackcdn.com/image/fetch/$s_!9s1L!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F39dab6b0-b957-4f04-949d-d6a777a5de30_306x326.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>Where &#8220;female&#8221; and &#8220;male&#8221; are the values stored in the Gender attribute column of the Customer Dimension.</p><p>A mistake I often see is developers using codes or keys for values in attributes. So, for example, in the database, &#8220;male&#8221; and &#8220;female&#8221; are represented as the codes M and F. If the M and F codes are carried through to the Dimension Table, then the pivot table report looks like this:</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!UBEC!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbc70ca52-ab0e-4f39-b5e9-efa52760b1f2_282x318.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!UBEC!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbc70ca52-ab0e-4f39-b5e9-efa52760b1f2_282x318.png 424w, /__u/substackcdn.com/image/fetch/$s_!UBEC!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbc70ca52-ab0e-4f39-b5e9-efa52760b1f2_282x318.png 848w, /__u/substackcdn.com/image/fetch/$s_!UBEC!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbc70ca52-ab0e-4f39-b5e9-efa52760b1f2_282x318.png 1272w, /__u/substackcdn.com/image/fetch/$s_!UBEC!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbc70ca52-ab0e-4f39-b5e9-efa52760b1f2_282x318.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!UBEC!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbc70ca52-ab0e-4f39-b5e9-efa52760b1f2_282x318.png" width="282" height="318" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/bc70ca52-ab0e-4f39-b5e9-efa52760b1f2_282x318.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:318,&quot;width&quot;:282,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!UBEC!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbc70ca52-ab0e-4f39-b5e9-efa52760b1f2_282x318.png 424w, /__u/substackcdn.com/image/fetch/$s_!UBEC!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbc70ca52-ab0e-4f39-b5e9-efa52760b1f2_282x318.png 848w, /__u/substackcdn.com/image/fetch/$s_!UBEC!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbc70ca52-ab0e-4f39-b5e9-efa52760b1f2_282x318.png 1272w, /__u/substackcdn.com/image/fetch/$s_!UBEC!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbc70ca52-ab0e-4f39-b5e9-efa52760b1f2_282x318.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>Which is far less useful. Users looking at this report may have no idea what M and F stand for. The codes M and F should be converted to their meaningful descriptive values.</p><p>Some rules for Dimension attributes:</p><ul><li><p>Operational codes (e.g. M for Male, F for Female) should be converted in Dimensions to their descriptive format (i.e. Male/Female).&nbsp;</p></li><li><p>True/False, Yes/No values should be converted to descriptions like &#8220;Is Contractor&#8221; or &#8220;Is Not Contractor.&#8221;</p></li></ul><p>Some red flags to watch out for:</p><ul><li><p>Dimension attributes should never be dates. Leave that to slowly changing dimension techniques, Calendar dimensions and various fact types.</p></li><li><p>Numerical values, especially contiguous values, should not be used as Attributes. See the next section.</p></li></ul><h4>Discrete vs Contiguous Dimension Attribute Values</h4><p>Dimension Table attributes should be discrete values, not contiguous values. What does this mean? Discrete values are drawn from a small set of distinct values, whereas continuous values can be any value (up to an infinite number) within a generally large range of possible values. A common example of a contiguous value that is often mistakenly used as a Dimension attribute is Product Price. For any given range of products a company sells, the product price could be any price between a range of say $0.01 and $10000.00. Its unlikely that any two products have the same price, which makes using price as a row or column header in a report not very useful. You will get a column or row for every price. See the example below. There is very little analytical value to a report like this:</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!rmkf!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc13944b5-7519-452d-a07f-f3b360cbd390_1044x64.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!rmkf!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc13944b5-7519-452d-a07f-f3b360cbd390_1044x64.png 424w, /__u/substackcdn.com/image/fetch/$s_!rmkf!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc13944b5-7519-452d-a07f-f3b360cbd390_1044x64.png 848w, /__u/substackcdn.com/image/fetch/$s_!rmkf!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc13944b5-7519-452d-a07f-f3b360cbd390_1044x64.png 1272w, /__u/substackcdn.com/image/fetch/$s_!rmkf!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc13944b5-7519-452d-a07f-f3b360cbd390_1044x64.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!rmkf!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc13944b5-7519-452d-a07f-f3b360cbd390_1044x64.png" width="1044" height="64" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/c13944b5-7519-452d-a07f-f3b360cbd390_1044x64.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:64,&quot;width&quot;:1044,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!rmkf!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc13944b5-7519-452d-a07f-f3b360cbd390_1044x64.png 424w, /__u/substackcdn.com/image/fetch/$s_!rmkf!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc13944b5-7519-452d-a07f-f3b360cbd390_1044x64.png 848w, /__u/substackcdn.com/image/fetch/$s_!rmkf!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc13944b5-7519-452d-a07f-f3b360cbd390_1044x64.png 1272w, /__u/substackcdn.com/image/fetch/$s_!rmkf!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc13944b5-7519-452d-a07f-f3b360cbd390_1044x64.png 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a></figure></div><p>To deal with this problem, a developer can turn the contiguous values into discrete values by defining groups of contiguous values. For example, a business might be interested in its sales of low-priced (&lt;=$99), medium-priced (&gt;$99 to &lt;$200), and high-priced (&gt;=$200) Products. By defining an attribute with values for each price range, the sales amount for each range can be aggregated and displayed. This is far more useful. See the image below:</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!2oJP!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F9085dc3c-9447-42ac-a63b-1c762f816d14_474x66.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!2oJP!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F9085dc3c-9447-42ac-a63b-1c762f816d14_474x66.png 424w, /__u/substackcdn.com/image/fetch/$s_!2oJP!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F9085dc3c-9447-42ac-a63b-1c762f816d14_474x66.png 848w, /__u/substackcdn.com/image/fetch/$s_!2oJP!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F9085dc3c-9447-42ac-a63b-1c762f816d14_474x66.png 1272w, /__u/substackcdn.com/image/fetch/$s_!2oJP!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F9085dc3c-9447-42ac-a63b-1c762f816d14_474x66.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!2oJP!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F9085dc3c-9447-42ac-a63b-1c762f816d14_474x66.png" width="474" height="66" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/9085dc3c-9447-42ac-a63b-1c762f816d14_474x66.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:66,&quot;width&quot;:474,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!2oJP!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F9085dc3c-9447-42ac-a63b-1c762f816d14_474x66.png 424w, /__u/substackcdn.com/image/fetch/$s_!2oJP!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F9085dc3c-9447-42ac-a63b-1c762f816d14_474x66.png 848w, /__u/substackcdn.com/image/fetch/$s_!2oJP!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F9085dc3c-9447-42ac-a63b-1c762f816d14_474x66.png 1272w, /__u/substackcdn.com/image/fetch/$s_!2oJP!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F9085dc3c-9447-42ac-a63b-1c762f816d14_474x66.png 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a></figure></div><h3>Row Management Columns</h3><p>A Dimension will also contain a set of &#8220;management&#8221; columns. Management columns are generally used by the ETL (extract, transform, load) process to help load data into the Dimension Table and to set properties of each row like latest flag, effective dates, etc.</p><h2>Slowly Changing Dimensions (SCD)</h2><p>Dimensions are often referred to as &#8216;<a href="https://www.dimodelo.com/blog/2024/slowly-changing-dimension/">Slowly Changing Dimensions</a>&#8217;. The term recognizes that Dimension Members are relatively static but change (albeit slowly) over time.</p><p>This is important because users are often interested in the impact to their reports of these changes to Dimensions over time. It&#8217;s necessary to define a number of change-handling strategies for Dimension Table attributes. Ralph Kimball defined these change-handling strategies as Slowly changing Dimension (SCD) types 1, 2, 3 and 4:</p><ul><li><p>SCD Type 1 &#8211; Don&#8217;t keep history, i.e. overwrite.</p></li><li><p>SCD Type 2 &#8211; Keep a version of the Dimension Member for every change.</p></li><li><p>SCD Type 3 &#8211; Keep the latest version and the prior version (but not every version).</p></li><li><p>SCD Type 4 &#8211; A hybrid combination of Type 2 and 3.</p></li></ul><p>The most commonly used SCD strategies are Types 1 and 2. SCD Types 3 and 4 are rarely used.</p><p>An important nuance to note is that, although we talk about Slowly Changing &#8220;Dimensions&#8221;, what we are actually implementing is Slowly Changing Attributes. You implement the change-handling strategy per Attribute. That means different attributes within one Dimension can have different &#8220;slowly changing Dimension&#8221; types. There are various techniques to achieve this. The short answer is to use one hash management column for columns of type 1 and a second hash for columns of type 2.</p><p>Read a more <a href="/__u/dimodelo.substack.com/p/slowly-changing-dimension/">in-depth description of Slowly Changing Dimensions</a>, including example code you can download and test for yourself.</p><h3>Slowly Changing Dimension Type 1 &#8211; Overwrite</h3><p>The slowly changing Dimension (SCD) type 1 change-handling strategy is applied; if a change occurs to an attribute, the existing attribute value is overwritten with the new value. Essentially, no history of the change is recorded.</p><p>A good candidate for an SCD Type 1 Attribute is something like Employee Name. If an employee&#8217;s name changes due to marriage, you don&#8217;t want two versions of the employee, one before marriage and one after. If you did and were looking at sales by employee, the employee would show up twice, once with the new name and once with the old. Instead, you want to overwrite the old name with the new name. In this scenario, the sales report by Employee would only show the Employee with the new name. Effectively all historical sales for that employee are now associated with the new name.</p><p>This highlights unanticipated consequences with SCD Type 1, and why you might want to adopt a different strategy (i.e. SCD Type 2). Let&#8217;s say you have a Sales Division Dimension, and each Sales Division has a parent Region. If the Sales Division is moved to a new Region, and the Region attribute of the Sales Division is treated as SCD Type 1, and overwritten with the new Region, then all the historical sales facts that were associated with the old Region would suddenly appear in Regional reports as if they had occurred in the new Region. Usually, an undesirable outcome. This is where SCD Type 2 comes into play.</p><h3>Slowly Changing Dimension Type 2 &#8211; Add a new Version</h3><p>In the SCD type 2 scenario, a new version of the Dimension member row is written when an SCD Type 2 Attribute changes. History is preserved. Existing Facts remain associated with the old version of the Dimension Member, and new Fact data is associated with the new version of the Dimension Member. For Example, let&#8217;s say you have a Sales Division Dimension, and each Sales Division has a parent Region attribute. A decision is made to move the Sales Division into a new Region. If the Region attribute of the Sales Division is treated as SCD type 2, then a new row is written to the Dimension Table for the new version of the Sales Division Dimension Member. There are now 2 rows in the Dimension for the same Division, one with the old Region, and one with the new Region.</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!nymP!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4ba1e265-69a5-4765-ab52-f12c8d1a93a4_874x144.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!nymP!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4ba1e265-69a5-4765-ab52-f12c8d1a93a4_874x144.png 424w, /__u/substackcdn.com/image/fetch/$s_!nymP!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4ba1e265-69a5-4765-ab52-f12c8d1a93a4_874x144.png 848w, /__u/substackcdn.com/image/fetch/$s_!nymP!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4ba1e265-69a5-4765-ab52-f12c8d1a93a4_874x144.png 1272w, /__u/substackcdn.com/image/fetch/$s_!nymP!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4ba1e265-69a5-4765-ab52-f12c8d1a93a4_874x144.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!nymP!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4ba1e265-69a5-4765-ab52-f12c8d1a93a4_874x144.png" width="874" height="144" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/4ba1e265-69a5-4765-ab52-f12c8d1a93a4_874x144.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:144,&quot;width&quot;:874,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;Slowly changing dimension SCD type 2 example&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="Slowly changing dimension SCD type 2 example" title="Slowly changing dimension SCD type 2 example" srcset="/__u/substackcdn.com/image/fetch/$s_!nymP!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4ba1e265-69a5-4765-ab52-f12c8d1a93a4_874x144.png 424w, /__u/substackcdn.com/image/fetch/$s_!nymP!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4ba1e265-69a5-4765-ab52-f12c8d1a93a4_874x144.png 848w, /__u/substackcdn.com/image/fetch/$s_!nymP!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4ba1e265-69a5-4765-ab52-f12c8d1a93a4_874x144.png 1272w, /__u/substackcdn.com/image/fetch/$s_!nymP!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4ba1e265-69a5-4765-ab52-f12c8d1a93a4_874x144.png 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a></figure></div><p>All the existing Sales facts associated with the old version remain associated with that version and would still appear in Regional reports as if they belong to the old Region. This is a desirable outcome because this region was responsible for each Sale at the time it was made. Only new Sales that occur after the change are associated with the Sales Division with the new Region, thus preserving history.</p><h3>Slowly Changing Dimension Type 3 &#8211; Latest and Prior Version</h3><p>SCD Type 3 change-handling strategy captures the latest and prior value of a Dimension attribute. It doesn&#8217;t capture every version. There are some rare circumstances where this is desirable. Take the previous example of a Division moving Regions. What if the business wanted to see today&#8217;s sales &#8220;as if&#8221; they were in the old region just to compare how they would have performed under the old sales organization? The SCD Type 2 strategy doesn&#8217;t accommodate this kind of request. This is because new sales are never associated with the old region. For a period of time, they may want to track sales in terms of the old regional divide vs the new regional divide.</p><p>Type three SCD satisfies this kind of reporting requirement. In the SCD Type 3 strategy, you don&#8217;t create a new row for the version of the Dimension member. Instead, a new column is added to capture the prior value.</p><p>For example:</p><p>Before the change the Richmond Division is in the &#8220;North&#8221; East Region:</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!6NPg!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd43d12d7-9e7f-48d5-a990-2666da3d9ca9_900x96.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!6NPg!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd43d12d7-9e7f-48d5-a990-2666da3d9ca9_900x96.webp 424w, /__u/substackcdn.com/image/fetch/$s_!6NPg!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd43d12d7-9e7f-48d5-a990-2666da3d9ca9_900x96.webp 848w, /__u/substackcdn.com/image/fetch/$s_!6NPg!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd43d12d7-9e7f-48d5-a990-2666da3d9ca9_900x96.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!6NPg!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd43d12d7-9e7f-48d5-a990-2666da3d9ca9_900x96.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!6NPg!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd43d12d7-9e7f-48d5-a990-2666da3d9ca9_900x96.webp" width="900" height="96" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/d43d12d7-9e7f-48d5-a990-2666da3d9ca9_900x96.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:96,&quot;width&quot;:900,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;scd type 3 before&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="scd type 3 before" title="scd type 3 before" srcset="/__u/substackcdn.com/image/fetch/$s_!6NPg!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd43d12d7-9e7f-48d5-a990-2666da3d9ca9_900x96.webp 424w, /__u/substackcdn.com/image/fetch/$s_!6NPg!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd43d12d7-9e7f-48d5-a990-2666da3d9ca9_900x96.webp 848w, /__u/substackcdn.com/image/fetch/$s_!6NPg!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd43d12d7-9e7f-48d5-a990-2666da3d9ca9_900x96.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!6NPg!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd43d12d7-9e7f-48d5-a990-2666da3d9ca9_900x96.webp 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a></figure></div><p>A &#8220;prior region&#8221; column is added to the table to accommodate the SCD type 3 change, and then the Richmond Division is moved to the &#8220;East Coast&#8221; Region. The result is as follows:</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!3KVn!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F44d52c13-99e7-46a7-86bf-a9b1e0fb005d_964x112.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!3KVn!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F44d52c13-99e7-46a7-86bf-a9b1e0fb005d_964x112.webp 424w, /__u/substackcdn.com/image/fetch/$s_!3KVn!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F44d52c13-99e7-46a7-86bf-a9b1e0fb005d_964x112.webp 848w, /__u/substackcdn.com/image/fetch/$s_!3KVn!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F44d52c13-99e7-46a7-86bf-a9b1e0fb005d_964x112.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!3KVn!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F44d52c13-99e7-46a7-86bf-a9b1e0fb005d_964x112.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!3KVn!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F44d52c13-99e7-46a7-86bf-a9b1e0fb005d_964x112.webp" width="964" height="112" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/44d52c13-99e7-46a7-86bf-a9b1e0fb005d_964x112.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:112,&quot;width&quot;:964,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;scd type 3 after&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="scd type 3 after" title="scd type 3 after" srcset="/__u/substackcdn.com/image/fetch/$s_!3KVn!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F44d52c13-99e7-46a7-86bf-a9b1e0fb005d_964x112.webp 424w, /__u/substackcdn.com/image/fetch/$s_!3KVn!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F44d52c13-99e7-46a7-86bf-a9b1e0fb005d_964x112.webp 848w, /__u/substackcdn.com/image/fetch/$s_!3KVn!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F44d52c13-99e7-46a7-86bf-a9b1e0fb005d_964x112.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!3KVn!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F44d52c13-99e7-46a7-86bf-a9b1e0fb005d_964x112.webp 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a></figure></div><p>Now all Sales Facts, new and old, are associated with the single version of the Dimension member, but analysts can choose either the current Region or Prior Region (or both) in their reports to compare current to prior Regional organization sales.</p><h2>Dimension Table Denormalization vs Normalization</h2><p>Dimensions often represent hierarchical relationships in the business. For example, take a Division-&gt;Region-&gt;Country hierarchy. In an operational system, these would normally be modelled as separate (normalized) tables with relationships between them. However, Dimensions tend to be denormalized. That is, instead of separate Dimension tables, we would have a single Division Dimension. The Division Dimension has a Region and Country attribute to model the relationship between a Division and its Region/Country. The hierarchical descriptive information is stored redundantly, but this design results in improved ease of use and query performance. Dimensions tend to have relatively few rows compared to Fact tables and a large number of columns. The trade-off with storage space is insignificant.</p><p>The exception would be if there were Facts in the Data Warehouse that had a grain at the Region or Country levels; then it&#8217;s necessary to have separate Dimensions for those levels so those Facts can be attached at that level.</p><h3>Snowflake Dimensions</h3><p>Snowflake dimensions describe hierarchical relationships in a Dimension table that have been &#8220;normalized.&#8221; Instead of a single Dimension Table with attributes representing relationships, secondary Dimension tables are created and connected to a base Dimension by an attribute key.</p><p>My advice (and Ralph Kimball&#8217;s) is to avoid them. They simply make the Data Warehouse harder to navigate, and nothing can be modelled in a Snowflake schema that can&#8217;t be modelled in a Star Schema.</p><p>Read <a href="/__u/dimodelo.substack.com/p/star-schema-vs-snowflake-schema/">Snowflake vs Star Schema</a> for more information</p><h2>The Two Types of Dimension Hierarchies</h2><h3>Natural Hierarchies</h3><p>Many dimensions contain natural relationships between attributes that form hierarchies. In our previous example, in the Division Dimension, there is a hierarchy from Country-&gt;Region-&gt;Division. This is known as a &#8220;natural&#8221; hierarchy because it is a relationship between attributes with a fixed depth or number of levels.</p><p>Hierarchies can be very useful for analysis, allowing drill-down and drill-up analysis in BI tools. BI tools can be configured to show these hierarchies as nested attributes making it easy to visualize and navigate the hierarchy.</p><p>It&#8217;s common for Dimensions to have multiple hierarchies. For example, a Calendar Dimension can have a Day&gt;Month&gt;Year&#8230; a Day&gt;Month&gt;Fiscal Year&#8230; a Day&gt;Month&gt;Quarter&gt;Year and a Day&gt;Fortnight&gt;Year hierarchies. All are valid Hierarchies, and all may be used by different people for different purposes.</p><p>Some Natural Hierarchy rules:</p><ul><li><p>Hierarchies in a Dimension always end with the root Attribute at the Grain of the Dimension. E.g. In the Calendar Dimension, the Day Attribute.</p></li><li><p>It&#8217;s important that each attribute value belongs to only one of its parent Attribute values. Otherwise, you have a broken Hierarchy.</p></li></ul><h3>Parent-Child Hierarchies</h3><p>A Parent-Child Hierarchy is a hierarchy of Dimension members where child members &#8220;point to&#8221; their parent members. Parent-child hierarchies are also known as Ragged or variable-depth Hierarchies because each &#8220;branch&#8221; of the Parent-Child &#8220;tree&#8221; can have a different number of levels.</p><p>Employees or Positions in an Organisation Chart are good examples of parent-child hierarchies. Each object points to its parent object, i.e., each Position in an Organisation Chart points to its parent Position.</p><p>These kinds of relationships are known as &#8220;recursive&#8221; relationships. Recursive relationships have traditionally been difficult for SQL and BI tools to navigate. Thankfully, today, most SQL dialects and good BI tools can natively query these relationships or emulate natural hierarchies based on the parent-child hierarchy.</p><p>Some Parent-Child Hierarchy rules:</p><ul><li><p>A Parent can have multiple children, but a child only has one parent.</p></li><li><p>The child contains an attribute that contains the identifier of its parent.</p></li></ul><h2>The Importance of Conformed Dimensions</h2><p>The Kimball method&nbsp;of Data Warehouse design describes a&nbsp;Data Warehouse Bus Matrix Architecture and&nbsp;the concept of &#8220;conformed&#8221; dimensions.&nbsp;Put simply, the concept of &#8220;conformed&#8221; Dimensions states that Facts should share common or &#8220;conformed&#8221; Dimensions to enable&nbsp;cross Datamart/Enterprise/Business process analysis.</p><p>The aim is to design your data warehouse so that Facts share as many Dimensions as possible. A data warehouse bus matrix is a good way to document the design of your Data Warehouse and maximize conformed Dimensions.</p><p>A <a href="https://www.dimodelo.com/blog/2023/what-is-a-data-warehouse-bus-matrix-and-why-you-need-one/">Data Warehouse matrix</a> documents the relationship between all planned Facts and Dimension Tables. By completing a matrix, you can see the overall high-level design of your Data Warehouse on a single sheet. In the image below, where there is a &#8220;1&#8221; at the intersection between Facts (the rows in blue) and Dimensions (the columns in green), there is a relationship between the Fact and the Dimension.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!Zcpp!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff66f16cf-4341-4cae-b3b9-a7a609c5aa46_690x349.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!Zcpp!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff66f16cf-4341-4cae-b3b9-a7a609c5aa46_690x349.png 424w, /__u/substackcdn.com/image/fetch/$s_!Zcpp!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff66f16cf-4341-4cae-b3b9-a7a609c5aa46_690x349.png 848w, /__u/substackcdn.com/image/fetch/$s_!Zcpp!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff66f16cf-4341-4cae-b3b9-a7a609c5aa46_690x349.png 1272w, /__u/substackcdn.com/image/fetch/$s_!Zcpp!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff66f16cf-4341-4cae-b3b9-a7a609c5aa46_690x349.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!Zcpp!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff66f16cf-4341-4cae-b3b9-a7a609c5aa46_690x349.png" width="690" height="349" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/f66f16cf-4341-4cae-b3b9-a7a609c5aa46_690x349.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:349,&quot;width&quot;:690,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;simple data warehouse matrix&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="simple data warehouse matrix" title="simple data warehouse matrix" srcset="/__u/substackcdn.com/image/fetch/$s_!Zcpp!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff66f16cf-4341-4cae-b3b9-a7a609c5aa46_690x349.png 424w, /__u/substackcdn.com/image/fetch/$s_!Zcpp!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff66f16cf-4341-4cae-b3b9-a7a609c5aa46_690x349.png 848w, /__u/substackcdn.com/image/fetch/$s_!Zcpp!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff66f16cf-4341-4cae-b3b9-a7a609c5aa46_690x349.png 1272w, /__u/substackcdn.com/image/fetch/$s_!Zcpp!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ff66f16cf-4341-4cae-b3b9-a7a609c5aa46_690x349.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>Conformed Dimensions are powerful. They allow cross-fact analysis. If two Facts share a Dimension, then, when a member is selected in that Dimension Table in a BI tool, it filters both Facts. For example, let&#8217;s say you have sales and accounting fact tables that are connected to the same calendar dimensions. You can select a Calendar period (e.g. Month), and select measures from both Fact tables (e.g. Sales Qty, and Revenue) in the same pivot table and they are both filtered by the Calendar Period member. See below:</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!r2wP!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2a9bc1b6-7ba9-4f83-813f-425ac91d2cb9_552x302.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!r2wP!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2a9bc1b6-7ba9-4f83-813f-425ac91d2cb9_552x302.webp 424w, /__u/substackcdn.com/image/fetch/$s_!r2wP!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2a9bc1b6-7ba9-4f83-813f-425ac91d2cb9_552x302.webp 848w, /__u/substackcdn.com/image/fetch/$s_!r2wP!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2a9bc1b6-7ba9-4f83-813f-425ac91d2cb9_552x302.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!r2wP!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2a9bc1b6-7ba9-4f83-813f-425ac91d2cb9_552x302.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!r2wP!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2a9bc1b6-7ba9-4f83-813f-425ac91d2cb9_552x302.webp" width="552" height="302" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/2a9bc1b6-7ba9-4f83-813f-425ac91d2cb9_552x302.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:302,&quot;width&quot;:552,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;conformed dimension pivot table example&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="conformed dimension pivot table example" title="conformed dimension pivot table example" srcset="/__u/substackcdn.com/image/fetch/$s_!r2wP!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2a9bc1b6-7ba9-4f83-813f-425ac91d2cb9_552x302.webp 424w, /__u/substackcdn.com/image/fetch/$s_!r2wP!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2a9bc1b6-7ba9-4f83-813f-425ac91d2cb9_552x302.webp 848w, /__u/substackcdn.com/image/fetch/$s_!r2wP!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2a9bc1b6-7ba9-4f83-813f-425ac91d2cb9_552x302.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!r2wP!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2a9bc1b6-7ba9-4f83-813f-425ac91d2cb9_552x302.webp 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>This also allows you to define calculated measures that use measures from more than one Fact table. For example, the &#8220;Avg Sale Amount&#8221; above which is Revenue/Sales Qty.</p><h2>Role Play and Junk Dimensions</h2><h3>Role Play Dimension</h3><p>A Fact can be associated with a Dimension in a different role more than once. These secondary associations are known as Role Play Dimensions. For example, a Task fact can be associated with the Calendar Dimension a number of times: once for a Scheduled date, once for a Started date, once for a Completed date and so on. Each of these would appear as separate Dimensions, i.e. the Started Calendar Dimension, the Scheduled Calendar Dimension and the Completed Calendar Dimension. This structure allows you to use the Scheduled Calendar, for example, to get the count of Tasks scheduled to start in a month. You could use both the Schedule and Started Calendars to get a count of Tasks that were both Scheduled and Started in a month. If you are directly querying your relational Data Warehouse, it&#8217;s useful to create a view for each role-play of the calendar. If you are using OLAP, it is not necessary.</p><h3>Junk Dimensions</h3><p>Transactions typically produce a set of miscellaneous, low-cardinality flags and indicators associated directly with the transaction. E.g. Sale Type, Sale Status etc. Our first instinct is to create a Sale Dimension to &#8220;house&#8221; these flags and indicators. However, a Sale Dimension would have one member for every Sale. That would mean the Dimension Table potentially has millions, hundreds of millions of rows, or even billions of rows. This would result in very poor performance.</p><p>Another remedy is to create a separate Dimension for each flag or indicator. However, this leads to a proliferation of Dimensions.</p><p>Rather than making separate dimensions for each flag, the best remedy is to combine them in a single &#8220;Junk&#8221; or degenerate dimension. Junk dimensions contain either the full Cartesian product of all attributes&#8217; possible values or a combination of just the values that actually occur in combination within the source data.</p><p>Using the <a href="https://byjus.com/maths/cartesian-products-of-sets/">cartesian product</a> is generally less resource-intensive. To generate a list of only existing combinations means scanning the whole source transaction table.</p><p>The more attributes you have in the Dimension, the bigger it gets. It&#8217;s important that the attributes are low cardinality. If you have 10 * 345 * 81 * 3 * 21 attribute values, you have 17M+ members. So you need to be careful what you include. In this case, perhaps the attribute with 345 values can be separated into its own dimension.</p><p>The business key of Junk Dimension is the combination of all attributes. When you do a lookup from the Fact to the Dimension to associate the correct member of the Junk Dimension, you need to combine all the attributes as the Lookup value. One tactic is to create a single business key column with a concatenation of the attribute values or a hash of the attribute values.</p>]]></content:encoded></item><item><title><![CDATA[What is a Fact table? (and why you need them)]]></title><description><![CDATA[In the context of a data warehouse, a fact table represents a business process or event and contains the measures and metrics you want to analyze for that process or event.]]></description><link>https://dimodelo.substack.com/p/what-is-a-fact-table-and-why-you-need-them</link><guid isPermaLink="false">https://dimodelo.substack.com/p/what-is-a-fact-table-and-why-you-need-them</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Thu, 28 Mar 2024 07:42:33 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/94e33202-2bc2-4139-a6f8-5fae5d32f9b7_702x332.webp" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>In the context of a <a href="/__u/dimodelo.substack.com/p/what-is-a-data-warehouse-and-why-you-need-one/">data warehouse</a>, a fact table represents a business process or event and contains the measures and metrics you want to analyze for that process or event. There are <a href="/__u/dimodelo.substack.com/i/160235460/the-types-of-fact-tables">three types of facts</a> corresponding to three kinds of business events.</p><p>A Fact doesn&#8217;t exist in isolation. It is related to a set of <a href="/__u/dimodelo.substack.com/p/dimension-tables-an-introduction/">Dimensions</a>. The Dimension Tables represent the business entities involved in the business process or event&#8212;the Who, What, Where, When, and Why of the business event. Dimensions provide context about the Fact.</p><p>Below is a diagram depicting an example &#8220;Job&#8221; Fact and its related dimensions &#8211; Customer, Calendar (i.e. Date), Time of Day, Employee and Address. It models a business event where Employees are sent on &#8220;Jobs&#8221; to mow lawns. Each Job is a business event and, therefore, can be modelled as a &#8220;Job&#8221; Fact.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!1bnE!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e149b92-5931-47b1-b0c0-0d1eb4afb945_702x332.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!1bnE!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e149b92-5931-47b1-b0c0-0d1eb4afb945_702x332.webp 424w, /__u/substackcdn.com/image/fetch/$s_!1bnE!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e149b92-5931-47b1-b0c0-0d1eb4afb945_702x332.webp 848w, /__u/substackcdn.com/image/fetch/$s_!1bnE!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e149b92-5931-47b1-b0c0-0d1eb4afb945_702x332.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!1bnE!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e149b92-5931-47b1-b0c0-0d1eb4afb945_702x332.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!1bnE!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e149b92-5931-47b1-b0c0-0d1eb4afb945_702x332.webp" width="702" height="332" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/4e149b92-5931-47b1-b0c0-0d1eb4afb945_702x332.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:332,&quot;width&quot;:702,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;Fact table example star schema&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="Fact table example star schema" title="Fact table example star schema" srcset="/__u/substackcdn.com/image/fetch/$s_!1bnE!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e149b92-5931-47b1-b0c0-0d1eb4afb945_702x332.webp 424w, /__u/substackcdn.com/image/fetch/$s_!1bnE!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e149b92-5931-47b1-b0c0-0d1eb4afb945_702x332.webp 848w, /__u/substackcdn.com/image/fetch/$s_!1bnE!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e149b92-5931-47b1-b0c0-0d1eb4afb945_702x332.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!1bnE!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e149b92-5931-47b1-b0c0-0d1eb4afb945_702x332.webp 1456w" sizes="100vw" fetchpriority="high"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Job Fact table &#8211; <a href="https://www.dimodelo.com/blog/2024/what-is-a-star-schema-and-why-its-important/">star schema</a></figcaption></figure></div><p>The Job Fact table contains the measures related to the Job. For example:</p><ul><li><p>The $ cost of the job (e.g. $200.00)</p></li><li><p>The duration of the job (e.g. 1.5 Hrs)</p></li><li><p>The sq meters of the job (e.g. 200 sqm)</p></li></ul><p>Measures, also known as metrics, are numerical values that can be aggregated; meaning they can be summed, averaged, or subjected to other mathematical operations. However, some measures are only semi-aggregable or non-aggregable. You can read further about measure additivity in the <a href="/__u/dimodelo.substack.com/i/160235460/the-types-of-measures-on-a-fact-table">&#8220;three types of measures&#8221;</a>.</p><p>A Fact table also contains a primary key (in this case, a &#8220;Job Id&#8221;) and the foreign keys to its dimensions. You can learn more in the <a href="/__u/dimodelo.substack.com/i/160235460/the-schema-of-a-fact-table">schema of a fact table</a> section.</p><p>A fact table works with its related Dimensions to support ad hoc analysis, reporting, and dashboards. For example, perhaps you want to know the average cost per sq meter for Pensioners. First, you select all jobs where the associated Customer has a Pensioner Status = true. Then, you apply a formula over the result set of fact rows to calculate the average cost per square meter&#8212;in this case, &#8220;sum(cost of job)/sum(sq meters).&#8221;</p><h2>Why do you need Fact tables?</h2><p>Fact tables are one element of a simple but powerful data modelling technique called <a href="https://www.dimodelo.com/blog/2024/what-is-dimensional-modeling-introduction/">dimensional modelling</a>. &nbsp;Dimensional modeling focuses on delivering simplicity for the end user. It allows users to easily understand and navigate the data available for reporting and ad hoc analysis. A dimensional model supports high-performance aggregated queries and supports many different analytics use cases.</p><h2>The 3 Types of Fact Tables</h2><p>There are 3 types of fact tables.</p><ol><li><p>Transaction Fact table</p></li><li><p>Accumulating Snapshot Fact table</p></li><li><p>Periodic Snapshot Fact Table</p></li></ol><p>The 3 types are derived from the 3 types of business events:</p><ul><li><p>Discrete business event (transaction fact)</p></li><li><p>Evolving business event (accumulating snapshot fact)</p></li><li><p>Recurring or Periodic business event (periodic snapshot fact)</p></li></ul><p>Each type of fact event/process is modelled differently.</p><h3>Transaction Fact Tables (Discrete Business Events)</h3><p>A transaction fact table is used to model discrete business events. Discrete events are &#8220;point in time&#8221; events, usually of short duration. They are typically atomic-level transactional events.</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!a4yO!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F542f5083-2200-40e2-bb26-0104e443d1f9_967x237.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!a4yO!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F542f5083-2200-40e2-bb26-0104e443d1f9_967x237.png 424w, /__u/substackcdn.com/image/fetch/$s_!a4yO!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F542f5083-2200-40e2-bb26-0104e443d1f9_967x237.png 848w, /__u/substackcdn.com/image/fetch/$s_!a4yO!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F542f5083-2200-40e2-bb26-0104e443d1f9_967x237.png 1272w, /__u/substackcdn.com/image/fetch/$s_!a4yO!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F542f5083-2200-40e2-bb26-0104e443d1f9_967x237.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!a4yO!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F542f5083-2200-40e2-bb26-0104e443d1f9_967x237.png" width="967" height="237" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/542f5083-2200-40e2-bb26-0104e443d1f9_967x237.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:237,&quot;width&quot;:967,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;transaction fact discrete business events&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="transaction fact discrete business events" title="transaction fact discrete business events" srcset="/__u/substackcdn.com/image/fetch/$s_!a4yO!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F542f5083-2200-40e2-bb26-0104e443d1f9_967x237.png 424w, /__u/substackcdn.com/image/fetch/$s_!a4yO!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F542f5083-2200-40e2-bb26-0104e443d1f9_967x237.png 848w, /__u/substackcdn.com/image/fetch/$s_!a4yO!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F542f5083-2200-40e2-bb26-0104e443d1f9_967x237.png 1272w, /__u/substackcdn.com/image/fetch/$s_!a4yO!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F542f5083-2200-40e2-bb26-0104e443d1f9_967x237.png 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a><figcaption class="image-caption">Discrete business events</figcaption></figure></div><p>&nbsp;Examples include:</p><ul><li><p>The customer buys a product.</p></li><li><p>A marketing email is sent.</p></li><li><p>A meter reading.</p></li><li><p>A visit to a website.</p></li></ul><p>Discrete events are completed at the moment they occur, or shortly after. Discrete events are generally associated with a single date and time.</p><p>Discrete Events are represented as&nbsp;<strong>Transaction Fact tables</strong>&nbsp;in the Data Warehouse.</p><p>A transaction Fact represents a discrete business event. It is often identified as a single record within a source database. It could be part of a larger business process, but this one event within the process generates its own record in the source database.</p><h3>Accumulating Snapshot Fact Table (Evolving Business Events)</h3><p>Evolving events are long-running business processes. They are often a series of&nbsp;<em>related</em>&nbsp;discrete events.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!LFs2!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F49bc4253-3f63-433d-abf7-a7371c7f9089_1033x326.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!LFs2!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F49bc4253-3f63-433d-abf7-a7371c7f9089_1033x326.png 424w, /__u/substackcdn.com/image/fetch/$s_!LFs2!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F49bc4253-3f63-433d-abf7-a7371c7f9089_1033x326.png 848w, /__u/substackcdn.com/image/fetch/$s_!LFs2!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F49bc4253-3f63-433d-abf7-a7371c7f9089_1033x326.png 1272w, /__u/substackcdn.com/image/fetch/$s_!LFs2!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F49bc4253-3f63-433d-abf7-a7371c7f9089_1033x326.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!LFs2!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F49bc4253-3f63-433d-abf7-a7371c7f9089_1033x326.png" width="1033" height="326" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/49bc4253-3f63-433d-abf7-a7371c7f9089_1033x326.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:326,&quot;width&quot;:1033,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;accumulating snapshot fact table evolving business events&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="accumulating snapshot fact table evolving business events" title="accumulating snapshot fact table evolving business events" srcset="/__u/substackcdn.com/image/fetch/$s_!LFs2!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F49bc4253-3f63-433d-abf7-a7371c7f9089_1033x326.png 424w, /__u/substackcdn.com/image/fetch/$s_!LFs2!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F49bc4253-3f63-433d-abf7-a7371c7f9089_1033x326.png 848w, /__u/substackcdn.com/image/fetch/$s_!LFs2!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F49bc4253-3f63-433d-abf7-a7371c7f9089_1033x326.png 1272w, /__u/substackcdn.com/image/fetch/$s_!LFs2!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F49bc4253-3f63-433d-abf7-a7371c7f9089_1033x326.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Evolving business events</figcaption></figure></div><p>Examples include:</p><ul><li><p>Purchasing: Requisition, Purchase order, Vendor Invoice, Delivery, Payment.</p></li><li><p>Home Care Visit: Scheduled, Started, Finished, Confirmed, Billed.</p></li><li><p>Mowing Job. Booked, Scheduled, Started, Completed.</p></li></ul><p>Evolving events are typically associated with multiple dates and times, one per discrete event in the series of related discrete events.</p><p>Evolving Events are modelled as&nbsp;<strong>accumulating snapshot Fact tables</strong>.</p><p>An accumulating snapshot fact captures multiple business process events within the one fact table. Usually, the events represent an entity proceeding through a series of known statuses. For example, a work item could go from proposed, to approved, to in progress, and complete. Each event has its own timestamp. Accumulating snapshot fact measures usually include the duration it takes to move between each event of the process and other measures of each event. Usually, each event of the process involves updating a single existing record in the source system. The history of the fact is captured by updating the timestamp on which the fact changes to each status within a single row.</p><h3>Periodic Snapshot Fact Table (Recurring Business Events)</h3><p>Recurring Events are period measurements that occur at predictable intervals, such as daily, weekly, monthly, etc.</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!MxDt!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F935ece69-6562-4c48-90d3-8091bd366e46_964x236.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!MxDt!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F935ece69-6562-4c48-90d3-8091bd366e46_964x236.png 424w, /__u/substackcdn.com/image/fetch/$s_!MxDt!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F935ece69-6562-4c48-90d3-8091bd366e46_964x236.png 848w, /__u/substackcdn.com/image/fetch/$s_!MxDt!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F935ece69-6562-4c48-90d3-8091bd366e46_964x236.png 1272w, /__u/substackcdn.com/image/fetch/$s_!MxDt!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F935ece69-6562-4c48-90d3-8091bd366e46_964x236.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!MxDt!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F935ece69-6562-4c48-90d3-8091bd366e46_964x236.png" width="964" height="236" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/935ece69-6562-4c48-90d3-8091bd366e46_964x236.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:236,&quot;width&quot;:964,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;periodic snapshot fact recuring business event&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="periodic snapshot fact recuring business event" title="periodic snapshot fact recuring business event" srcset="/__u/substackcdn.com/image/fetch/$s_!MxDt!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F935ece69-6562-4c48-90d3-8091bd366e46_964x236.png 424w, /__u/substackcdn.com/image/fetch/$s_!MxDt!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F935ece69-6562-4c48-90d3-8091bd366e46_964x236.png 848w, /__u/substackcdn.com/image/fetch/$s_!MxDt!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F935ece69-6562-4c48-90d3-8091bd366e46_964x236.png 1272w, /__u/substackcdn.com/image/fetch/$s_!MxDt!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F935ece69-6562-4c48-90d3-8091bd366e46_964x236.png 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a><figcaption class="image-caption">Recurring business events</figcaption></figure></div><p>Examples include:</p><ul><li><p>Balance Sheet. Financial Account Balances.</p></li><li><p>Nightly Balance for Bank Accounts.</p></li></ul><p>Recurring events are typically used to sample and summarize discrete events, especially where cumulative measures are required. Balances are stored because deriving the balance from the start of time by summing all discrete events for an account is expensive.</p><p>Recurring Events are modeled as&nbsp;<strong>periodic snapshot Fact tables</strong>.</p><p>A periodic snapshot fact captures the aggregate or balance of a business process or event for a given period. Common examples are monthly financial account balances, monthly bank account balances, etc. Periodic Snapshot fact tables are usually built from the data contained in a transaction fact table. They start with an opening balance (from the previous period) tally up the transactions for the current period and produce a closing balance. However, periodic snapshot fact tables may also represent aggregations (SUM, AVG, etc) of a period. For example, at the end of each day, the rolling 12-month sum of Asset failure minutes. The fact is a historical snapshot at a point in time.</p><h3>Factless Fact Table</h3><p>Okay, Okay. I know I said there were 3 types, but this is the exception to the rule! A factless table is designed to simply acknowledge the existence of a relationship between 2 or more dimensions. There is no business event.</p><p>A good example can be found in companies that manage electrical assets. The poles and wires that deliver electricity to houses. Imagine you wanted to count the number of assets of a particular type that exist within a region. An Asset factless Fact table with relationships to an Asset and Region dimensions would serve this purpose.</p><p>Why is it called a factless fact table? An &#8220;eventless&#8221; fact table would be a better description since no event needs to occur to record the existence of the relationship. Another description might be a &#8220;measureless&#8221; fact table since factless fact tables are assumed to have no measures. But even that is a misnomer. A factless fact table does, in fact, have a single measure: a &#8220;count&#8221; measure. I think the confusion arises because it&#8217;s not necessary to explicitly put a count measure column on a fact table to be able to count rows. As a rule, I always explicitly add a count measure column, with a value of 1 in every row. It makes it clearer why the factless fact table exists, and makes it easy to create the count measure in a <a href="/__u/dimodelo.substack.com/p/what-is-a-semantic-layer-what-why-how-and-more/">semantic layer</a>.</p><p>Is a factless fact table a &#8220;design smell&#8221;? Not exactly, but it could indicate you haven&#8217;t considered the nature of the &#8220;exists&#8221; relationship. Especially if you throw in Calendar/Time as a dimension. When does the relationship exist? When did the relationship start to exist, and when did it cease? This thinking can often lead you to build an accumulating snapshot fact table. In our Asset example, consider the lifecycle of the Asset. It&#8217;s planned, constructed, enters operation, and retired. All of these events occur at a point in time. If you created an accumulating snapshot fact that matched the business process, you can still answer the original question, &#8220;Count the number of assets of a particular type that exist within a region&#8221;, but it also adds the ability to enhance that question to &#8220;Count the number of <strong>operational</strong> assets of a particular type that existed within a region <strong>at the end of FY 26</strong>&#8220;, which is probably a more accurate request, that better matches the users intent.</p><h2>Facts vs Dimension table</h2><p>Facts and dimensions serve different purposes but work in concert to support reporting and analytics.</p><p>As discussed previously, a Fact table represents a business process or event. It contains the measures/numbers you want to analyze, whereas Dimensions are a business entity related to the business event the Fact represents. A business entity is the people, places, and things that perform a business process or event.</p><p>The Fact only contains the measures (e.g., $, quantity, count, duration, etc.) related to the business event and foreign keys to the related dimensions. The Dimensions contain the context/qualitative attributes of the related business entities. For example, a Customer dimension might have attributes like Name, Gender, Pensioner Status, Has a Dog, etc.</p><p>Facts and Dimensions exist together in a <a href="/__u/dimodelo.substack.com/p/what-is-a-star-schema-and-why-its-important/">Star Schema</a>. When analysts use the star schema to answer a business question, they filter the facts by selected dimensional attributes. E.g. &#8220;Select Facts related to Customers where HasADog = &#8216;true'&#8221;, then aggregates a measure to produce a value E.g. &#8220;Select AVG(duration) From Facts related to Customers where HasADog = &#8216;true'&#8221;</p><h2>The schema of a fact table</h2><p>A Fact table contains four types of columns:</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!iqch!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F93cc49f6-0c73-4550-81a7-74ce55ed181b_362x483.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!iqch!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F93cc49f6-0c73-4550-81a7-74ce55ed181b_362x483.png 424w, /__u/substackcdn.com/image/fetch/$s_!iqch!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F93cc49f6-0c73-4550-81a7-74ce55ed181b_362x483.png 848w, /__u/substackcdn.com/image/fetch/$s_!iqch!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F93cc49f6-0c73-4550-81a7-74ce55ed181b_362x483.png 1272w, /__u/substackcdn.com/image/fetch/$s_!iqch!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F93cc49f6-0c73-4550-81a7-74ce55ed181b_362x483.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!iqch!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F93cc49f6-0c73-4550-81a7-74ce55ed181b_362x483.png" width="362" height="483" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/93cc49f6-0c73-4550-81a7-74ce55ed181b_362x483.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:483,&quot;width&quot;:362,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;Fact table schema&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="Fact table schema" title="Fact table schema" srcset="/__u/substackcdn.com/image/fetch/$s_!iqch!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F93cc49f6-0c73-4550-81a7-74ce55ed181b_362x483.png 424w, /__u/substackcdn.com/image/fetch/$s_!iqch!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F93cc49f6-0c73-4550-81a7-74ce55ed181b_362x483.png 848w, /__u/substackcdn.com/image/fetch/$s_!iqch!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F93cc49f6-0c73-4550-81a7-74ce55ed181b_362x483.png 1272w, /__u/substackcdn.com/image/fetch/$s_!iqch!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F93cc49f6-0c73-4550-81a7-74ce55ed181b_362x483.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Example Fact table schema</figcaption></figure></div><ol><li><p><strong>Measures</strong>. Measures are the &#8220;numbers&#8221; or metrics by which you &#8220;measure&#8221; your business process/event. Typically, a measure is an amount, count, $ value, duration, area, length, ratio, etc. A measure is always numeric. A fact table can have multiple measures.</p></li><li><p><strong>Foreign Keys to Dimensions</strong>. Facts contain a foreign key to each Dimension associated with the Fact. Typically, the relationship is with the surrogate key of the dimension. These foreign keys are the &#8220;link&#8221; that allows Fact tables to be filtered by the attributes of the Dimensions.</p></li><li><p><strong>Primary Key</strong>. The primary key is the unique key used by the source of the Fact to identify a unique instance of the business event. E.g. job_id in the source Job management system. A primary key can be a composite key. A primary key is important. The ETL process uses it to determine if it needs to insert or update a row. There should be only one row in the fact per primary key. See the &#8220;<a href="#understanding_fact_table_grain">Fact table grain</a>&#8221; for more details.</p></li><li><p><strong>Management Columns</strong>. Management columns are used by the ETL process and occasionally at query time. They provide metadata about the row. Examples include effective dates, deleted indicators, latest indicators, and batch load IDs.</p></li></ol><p>A Fact is designed to be &#8220;narrow and long&#8221; versus dimensions which are typically &#8220;short and wide&#8221;. A fact table could contain billions of rows (i.e. long). It&#8217;s desirable to store as few columns as possible (i.e. narrow) to aid performance. The contextual information (which is generally substantial) is offloaded to the &#8220;short and wide&#8221; dimensions. Dimensions typically contain fewer rows (they are not generally transactional in nature) but contain many columns representing all the attributes of the business entity they represent.</p><p>Typically, end users only see the measures via a semantic layer. The other columns are hidden. They are only required by the ETL process or the underlying semantic model and query engine.</p><h2>The 3 types of measures on a Fact table</h2><p>Additivity is a crucial concept when discussing measures. In general, analytical queries retrieve thousands or millions of rows. Once retrieved the measures are aggregated in some way. The default aggregation of most semantic and BI tools is to add, or in other words, sum the values.</p><ul><li><p><strong>Additive</strong>. A measure is additive if it can be summed across any combination of dimensions to produce a sensible result. For example, imagine a sales fact with a <em>sales_amount</em> measure. A user can use any combination of dimension attributes to filter the fact rows and still sum the sales amount to get total sales.</p></li><li><p><strong>Semi-additive</strong>. Semiadditive measures can be added only along some of the dimensions. Usually semiadditive measures can&#8217;t be added across the calendar/date dimension. This is especially true for period snapshot fact tables. For example imagine a Monthly Inventory period snapshot fact with an end_of_month_product_balance measure. For a given month, you can add the balances of different products to get a total balance for a Product Category (an attribute of a Product Dimension). However, you can&#8217;t add the end_of_month_product_balance product balance for January + February + March (Month attribute from the Calendar/Date Dimension) to produce an end_of_quarter_balance. This doesn&#8217;t make sense. Instead you need to use a different aggregation (e.g. Count, MAX, MIN or AVG) over the Calendar/Date Dimension after summing across all other dimensions.</p></li><li><p><strong>Non-additive</strong>. Non-additive measures can&#8217;t be added at all. Nonadditive measures must use a different aggregation (e.g. Count, MAX, MIN, but not AVG) over all dimensions. Measures that are percentages and ratios, such as gross margin, are always nonadditive. Percentages and ratios cannot be averaged either. Instead of storing nonadditive measures in the fact table, it is better to store the numerator and denominator. The ratio can be calculated in the semantic layer or reporting tool later. When calculating the ratio, ensure you calculate the &#8220;ratio of the sums&#8221;, not the &#8220;sum of the ratios&#8221;.</p></li></ul><p>A good example is <em>unit_price</em>. <em>unit_price</em> is the ratio <em>sale_amt</em>/<em>units_sold</em>. See the image below of analysis of 12 sales of a given product.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!Jp-8!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a0a0e37-bbb1-4356-80b0-7a8fb8b55fa2_610x477.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!Jp-8!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a0a0e37-bbb1-4356-80b0-7a8fb8b55fa2_610x477.png 424w, /__u/substackcdn.com/image/fetch/$s_!Jp-8!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a0a0e37-bbb1-4356-80b0-7a8fb8b55fa2_610x477.png 848w, /__u/substackcdn.com/image/fetch/$s_!Jp-8!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a0a0e37-bbb1-4356-80b0-7a8fb8b55fa2_610x477.png 1272w, /__u/substackcdn.com/image/fetch/$s_!Jp-8!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a0a0e37-bbb1-4356-80b0-7a8fb8b55fa2_610x477.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!Jp-8!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a0a0e37-bbb1-4356-80b0-7a8fb8b55fa2_610x477.png" width="610" height="477" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/3a0a0e37-bbb1-4356-80b0-7a8fb8b55fa2_610x477.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:477,&quot;width&quot;:610,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!Jp-8!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a0a0e37-bbb1-4356-80b0-7a8fb8b55fa2_610x477.png 424w, /__u/substackcdn.com/image/fetch/$s_!Jp-8!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a0a0e37-bbb1-4356-80b0-7a8fb8b55fa2_610x477.png 848w, /__u/substackcdn.com/image/fetch/$s_!Jp-8!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a0a0e37-bbb1-4356-80b0-7a8fb8b55fa2_610x477.png 1272w, /__u/substackcdn.com/image/fetch/$s_!Jp-8!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a0a0e37-bbb1-4356-80b0-7a8fb8b55fa2_610x477.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>Summing unit price across any of the dimensions results in a nonsense number. Therefore it is nonadditive. Averaging unit_price results in an incorrect value because you are &#8220;summing the ratios&#8221; instead of the &#8220;ratio of the sums&#8221;. In order to analyze the average unit_price for a product, you do the &#8220;ratio of the sums&#8221;, which is sum( sales_amt)/sum(units_sold). The MIN or MAX unit_price is a valid aggregation.</p><p>A fact can contain a mix of additive, semi-additive and non-additive measures. For example, imagine the inventory fact discussed. It could have the additive measure <em>total_units_sold</em>, the semi-additive measure <em>end_of_month_product_balance</em>, and the non-additive measure <em>avg_unit_price</em>.</p><h2>Understanding Fact Table grain</h2><p>The &#8220;grain&#8221; of a fact table describes the lowest level of detail available in the fact table. It provides the answer to the question, &#8220;How do you describe a single row in the fact table?&#8221; The atomic level of a fact table aligns with its primary key.</p><p>In the case of a transaction fact table. the preference is to store data at the most atomic level captured by a business process. Atomic data is the most detailed information available.</p><p>Examples of the grain of transaction facts are:</p><ul><li><p>An individual line item on a retail sales receipt. The primary key is sales_id and line item number.</p></li><li><p>An individual product produced. The primary key is a product serial number.</p></li><li><p>An individual mowing job is done. The primary key is the job_id.</p></li></ul><p>Period snapshot facts have a grain that includes a snapshot business process and a calendar interval. For example:</p><ul><li><p>A daily snapshot of the inventory levels for each product in a warehouse. The primary key is product and day.</p></li><li><p>A monthly balance for each bank account. The primary key is the account and month.</p></li></ul><p>All measures on a Fact table share the same grain. If a measure exists at a different grain, you need another fact.</p><p>There is a misconception that the grain of a fact aligns with the intersection of all its dimensions. This isn&#8217;t true. It&#8217;s typical for a fact to exist that doesn&#8217;t yet have all of its possible dimensions. Instead, it is the atomic level of detail of the underlying business process.</p><p>There is also a misconception that <a href="/__u/dimodelo.substack.com/p/what-is-dimensional-modeling-introduction/">dimensional models</a> should only contain summarized data. This mistake invites the criticism that the dimensional model needs to anticipate the business questions at various grains. Fact tables with grains that represent a higher aggregation of the most atomic data are limited to fewer and less detailed dimensions. Less granular facts inevitably run into issues when users try to drill down into details.</p><p>In contrast, an atomic fact offers the utmost analytical flexibility. It can be filtered and aggregated in every conceivable manner, across detailed dimensions, at all levels of granularity. Atomic data within a dimensional model can accommodate a variety of unforeseen use cases and ad-hoc analyses.</p><p>And don&#8217;t forget, you can have more than 1 fact table! It&#8217;s typical for a data warehouse to have more than one type of fact for the same business process. Typically, you would couple a transaction or Accumulating Snapshot fact with a periodic snapshot fact.</p><p>For example:</p><ul><li><p>An inventory transaction fact. I.e. Add to inventory and take from inventory transactions.</p></li><li><p>A monthly periodic snapshot of inventory balances.</p></li></ul><p>Why have different types of facts for the same business process? Because each one can answer different questions.</p><p>Don&#8217;t try to mix grains to fit into a single fact. An example where people make this mistake is a sales fact. Certain measures exist at the line item level, e.g. num_of_units and $ amount. Other measures only exist at the Sale level, like discount_given, and sales_tax. You could try apportioning the discount to the line item level, but a better and easier approach is having 2 facts. A fact at the sale grain and a fact at the sale_line_item grain. You use conformed dimensions to allow analysis across these two facts, but that&#8217;s a story for a different article.</p>]]></content:encoded></item><item><title><![CDATA[What is Dimensional Modeling (introduction)]]></title><description><![CDATA[Dimensional modeling is a data modeling technique used to model the presentation layer of a data warehouse. It focuses on delivering simplicity and query performance for the end user.]]></description><link>https://dimodelo.substack.com/p/what-is-dimensional-modeling-introduction</link><guid isPermaLink="false">https://dimodelo.substack.com/p/what-is-dimensional-modeling-introduction</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Tue, 19 Mar 2024 07:14:23 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/66e00be4-0462-47ce-a656-8525886df3ed_672x524.webp" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>Dimensional modeling is a data modeling technique used to model the presentation layer of a <a href="https://www.dimodelo.com/blog/2024/what-is-a-data-warehouse-and-why-you-need-one/">data warehouse</a>. It focuses on delivering simplicity and query performance for the end user. It allows users to easily understand and navigate the data available for reporting and ad hoc analysis. A dimensional model supports high-performance aggregated queries and performs well over many different analytics use cases.</p><p>Dimensional modelling is broadly accepted across the industry. It was first popularized by Ralph Kimball. Ralph Kimball&#8217;s data warehouse methodology remains relevant, even today, with the advent of Data Lakes and Data Lakehouses. In the Kimball methodology, a dimensional model is delivered using a modelling technique known as the &#8220;star&#8221; schema.</p><h2>The 3 essential building blocks of Dimensional Data Modeling</h2><p>A dimensional data model consists of 2 types of tables (Facts and Dimensions) and their relationships. Thus it&#8217;s simplicity. Facts and Dimensions are related together and arranged in a &#8220;star&#8221; schema. The image below is an <strong>example star schema</strong>. It depicts an imaginary video streaming company, GetFlix, and a &#8220;Shows Viewed&#8221; fact table. The &#8220;Shows Viewed&#8221; fact table is at the centre of the <a href="https://www.dimodelo.com/blog/2024/what-is-a-star-schema-and-why-its-important/">Star Schema</a> and surrounded by its Dimensions.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!-ahQ!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0d3d5408-2693-4de7-aac5-5a5b3c3e46f8_672x524.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!-ahQ!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0d3d5408-2693-4de7-aac5-5a5b3c3e46f8_672x524.webp 424w, /__u/substackcdn.com/image/fetch/$s_!-ahQ!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0d3d5408-2693-4de7-aac5-5a5b3c3e46f8_672x524.webp 848w, /__u/substackcdn.com/image/fetch/$s_!-ahQ!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0d3d5408-2693-4de7-aac5-5a5b3c3e46f8_672x524.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!-ahQ!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0d3d5408-2693-4de7-aac5-5a5b3c3e46f8_672x524.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!-ahQ!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0d3d5408-2693-4de7-aac5-5a5b3c3e46f8_672x524.webp" width="672" height="524" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/0d3d5408-2693-4de7-aac5-5a5b3c3e46f8_672x524.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:524,&quot;width&quot;:672,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!-ahQ!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0d3d5408-2693-4de7-aac5-5a5b3c3e46f8_672x524.webp 424w, /__u/substackcdn.com/image/fetch/$s_!-ahQ!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0d3d5408-2693-4de7-aac5-5a5b3c3e46f8_672x524.webp 848w, /__u/substackcdn.com/image/fetch/$s_!-ahQ!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0d3d5408-2693-4de7-aac5-5a5b3c3e46f8_672x524.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!-ahQ!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0d3d5408-2693-4de7-aac5-5a5b3c3e46f8_672x524.webp 1456w" sizes="100vw" fetchpriority="high"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Getflix &#8220;Shows Viewed&#8221; fact star schema</figcaption></figure></div><p>The following is a brief introduction to these concepts.</p><h3>Facts tables</h3><p>A <a href="https://www.dimodelo.com/topic/fact-concepts/">Fact table</a> represents a business process or an event within a business process. It contains the measures/numbers you want to analyse. For example, the &#8220;GetFlix&#8221; &#8220;Shows Viewed&#8221; fact table depicted in the star schema example above contains one row for every time a customer views an Episode of a Show. &#8220;Customer views an Episode of a Show&#8221; is the business event we are measuring.</p><h3>Dimensions</h3><p>A <a href="https://www.dimodelo.com/blog/2024/dimension-tables-an-introduction/">Dimension</a> represents a business entity, which is the people, places, and things that come together to perform business activities. A Dimension contains the attributes (i.e. fields) of the business entity, e.g., Customer Gender, Age, Category, etc. The attributes are used to filter and group fact data when performing data warehousing queries.</p><h3>Star Schema</h3><p>A <a href="https://www.dimodelo.com/topic/the-star-schema/">Star Schema</a> refers to how Facts and Dimensions are related in a Data Warehouse. A Star Schema is organized around a central fact table that is related to its Dimension tables using foreign keys in the fact table. The name &#8220;star&#8221; schema refers to the star-like pattern that emerges when you present the Fact table and its Dimensions in an entity-relationship diagram. See the example above.</p><h2>How to Build a Dimensional Data Model</h2><p>Using the 3 essential dimensional data modeling building blocks discussed above a data warehouse modeler can build an entire data warehouse data model.</p><p>Very briefly, the process is:</p><ol><li><p>Identify the business process.</p></li><li><p>Identify the grain (i.e. unique key) of the fact or fact(s) of the business process.</p></li><li><p>Identify the Who, What, When, Where and Why are involved in the business process. The Dimensions of your star schema.</p></li><li><p>Identify the sources of data. Write the code to extract the data into the data warehouse.</p></li><li><p>Write code to transform the data into a form suitable to be loaded into the presentation layer of the data warehouse.</p></li><li><p>Write code to load the data into the presentation layer of the data warehouse modeled as a star schema.</p></li></ol><p>Obviously, there is a lot more to it than that. Data warehouse data modeling and architecture is a specialized field that benefits from training and years of experience. This is just a quick overview.</p><h2>Star Schema vs Enterprise Data Warehouse Data Model</h2><p>So far, we have discussed using a star schema. However, a star schema only describes a single Fact table. An Enterprise data warehouse should model many different business processes/events, each with its own Fact table and related Dimensions joined in a star schema.</p><p>The question is, how do we prevent duplication of the Dimensions used by Facts and facilitate cross-business process analysis?</p><p>The answer is &#8220;Conformed&#8221; Dimensions. Essentially, a conformed Dimension is a Dimension shared by many facts. Typical conformed Dimensions are key business entities like Employees, Customers, Products, Cost Centres, Dates, and Times.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!CxAS!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd3a1a762-b241-4620-8ee3-4a4f65d1c32f_750x566.webp" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!CxAS!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd3a1a762-b241-4620-8ee3-4a4f65d1c32f_750x566.webp 424w, /__u/substackcdn.com/image/fetch/$s_!CxAS!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd3a1a762-b241-4620-8ee3-4a4f65d1c32f_750x566.webp 848w, /__u/substackcdn.com/image/fetch/$s_!CxAS!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd3a1a762-b241-4620-8ee3-4a4f65d1c32f_750x566.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!CxAS!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd3a1a762-b241-4620-8ee3-4a4f65d1c32f_750x566.webp 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!CxAS!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd3a1a762-b241-4620-8ee3-4a4f65d1c32f_750x566.webp" width="750" height="566" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/d3a1a762-b241-4620-8ee3-4a4f65d1c32f_750x566.webp&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:566,&quot;width&quot;:750,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!CxAS!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd3a1a762-b241-4620-8ee3-4a4f65d1c32f_750x566.webp 424w, /__u/substackcdn.com/image/fetch/$s_!CxAS!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd3a1a762-b241-4620-8ee3-4a4f65d1c32f_750x566.webp 848w, /__u/substackcdn.com/image/fetch/$s_!CxAS!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd3a1a762-b241-4620-8ee3-4a4f65d1c32f_750x566.webp 1272w, /__u/substackcdn.com/image/fetch/$s_!CxAS!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fd3a1a762-b241-4620-8ee3-4a4f65d1c32f_750x566.webp 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Enterprise data warehouse with conformed dimensions (in red)</figcaption></figure></div><p>When two Fact tables share a Dimension, you can produce a report with measures side-by-side from both Fact tables, categorized or filtered by attributes of their conformed (i.e. shared) Dimensions. In this way, dimensional modeling with conformed Dimensions supports enterprise-wide cross-business process analysis.</p><p>Another way of representing conformed dimensions is through a <a href="https://www.dimodelo.com/blog/2023/what-is-a-data-warehouse-bus-matrix-and-why-you-need-one/">data warehouse matrix</a>.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!I4FV!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fccb6bfba-03ce-4f47-8d4b-f2d94b463e90_697x374.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!I4FV!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fccb6bfba-03ce-4f47-8d4b-f2d94b463e90_697x374.png 424w, /__u/substackcdn.com/image/fetch/$s_!I4FV!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fccb6bfba-03ce-4f47-8d4b-f2d94b463e90_697x374.png 848w, /__u/substackcdn.com/image/fetch/$s_!I4FV!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fccb6bfba-03ce-4f47-8d4b-f2d94b463e90_697x374.png 1272w, /__u/substackcdn.com/image/fetch/$s_!I4FV!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fccb6bfba-03ce-4f47-8d4b-f2d94b463e90_697x374.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!I4FV!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fccb6bfba-03ce-4f47-8d4b-f2d94b463e90_697x374.png" width="697" height="374" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/ccb6bfba-03ce-4f47-8d4b-f2d94b463e90_697x374.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:374,&quot;width&quot;:697,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!I4FV!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fccb6bfba-03ce-4f47-8d4b-f2d94b463e90_697x374.png 424w, /__u/substackcdn.com/image/fetch/$s_!I4FV!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fccb6bfba-03ce-4f47-8d4b-f2d94b463e90_697x374.png 848w, /__u/substackcdn.com/image/fetch/$s_!I4FV!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fccb6bfba-03ce-4f47-8d4b-f2d94b463e90_697x374.png 1272w, /__u/substackcdn.com/image/fetch/$s_!I4FV!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fccb6bfba-03ce-4f47-8d4b-f2d94b463e90_697x374.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">example data warehouse bus matrix</figcaption></figure></div>]]></content:encoded></item><item><title><![CDATA[Gathering Requirements and Designing a Data Warehouse]]></title><description><![CDATA[How do you gather requirements for a Data Warehouse/Data Lakehouse project?]]></description><link>https://dimodelo.substack.com/p/gathering-requirements-and-designing-a-data-warehouse</link><guid isPermaLink="false">https://dimodelo.substack.com/p/gathering-requirements-and-designing-a-data-warehouse</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Tue, 19 Mar 2024 03:59:00 GMT</pubDate><enclosure url="https://substackcdn.com/image/fetch/$s_!Iz6N!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F428f4954-4b32-436c-b70d-1bb140698e1c_788x1620.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>How do you gather requirements for a Data Warehouse/Business Intelligence project?</p><p>Typically, on a BI project, if you ask a business user, &#8216;what do you want&#8217; you will get one of 2 responses.</p><ol><li><p>I don&#8217;t know.</p></li><li><p>I want everything.</p></li></ol><p>Which are, effectively, the same thing&#8230;</p><p>As much as it pains IT people to hear these responses, if you think about it, they are actually the right answer. From day to day, a business user, especially any analyst in a business, doesn&#8217;t know how they will want to view and analyse their data. They are responding to changing business environment on a day to day basis. The BI team&#8217;s job is to deliver the capability to analyse data in a variety of ways to these business users.</p><p>Gathering requirements for a Data Warehouse project is different to Operational systems. In Operational systems, you can start with a blank sheet of paper, and build exactly what the user wants. On a Data Warehouse project, you are highly constrained by what data your source systems produce. Therefore letting an end user go wild with all kinds of esoteric requirements can lead to horrible disappointment.</p><p>There is no silver bullet. Like on most projects, you have to work with what&#8217;s in front of you. Organisations undertaking BI projects all start with very different levels of vision, understanding and expertise. Each situation calls for a unique approach. However, one thing we find is true is that the requirements gathering process is as much an education process as it is a requirements gathering exercise. Most business users are unaware of the possibilities of BI, and will often describe their requirements in terms of what they have had before (e.g. A list all sales for June that I can import into Excel&#8230;)</p><p>Building a Data Warehouse is mostly about building capability, rather than delivering specific report outcomes. It&#8217;s a mistake to take a &#8216;Business Intelligence&#8217; requirement (i.e. this Report, that report&#8230; etc) and build a data Warehouse just to satisfy the reporting requirement. Tomorrow, a new requirement might arise, which would fundamentally change the Data Warehouse (Usually the detail level, known as the grain, of a Fact table).</p><p>In the next sections, we outline 3 different approaches to gathering business requirements for a data warehouse.</p><h2><strong>Ontology</strong></h2><p>The mantra for Data Warehouse design is &#8220;Model Reality&#8221;. In previous lessons, we have discussed how Facts represent Business Events/Processes and Dimensions represent business entities.</p><p>The natural way to understand the requirements of the Data Warehouse is to simply describe the Business Entities and Processes.</p><p>To do this we recommend writing an Ontology. An Ontology is a big word for a simple concept:</p><ul><li><p><strong>Ontology: &#8220;a set of concepts and categories in a subject area that shows their properties and the relations between them.&#8221;</strong></p></li></ul><p>Keeping things simple, we recommend creating a document with the following format:</p><h3><strong>Business Process</strong></h3><p>Below is an example of a Business Process description in an Ontology document:</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!Iz6N!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F428f4954-4b32-436c-b70d-1bb140698e1c_788x1620.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!Iz6N!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F428f4954-4b32-436c-b70d-1bb140698e1c_788x1620.png 424w, /__u/substackcdn.com/image/fetch/$s_!Iz6N!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F428f4954-4b32-436c-b70d-1bb140698e1c_788x1620.png 848w, /__u/substackcdn.com/image/fetch/$s_!Iz6N!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F428f4954-4b32-436c-b70d-1bb140698e1c_788x1620.png 1272w, /__u/substackcdn.com/image/fetch/$s_!Iz6N!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F428f4954-4b32-436c-b70d-1bb140698e1c_788x1620.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!Iz6N!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F428f4954-4b32-436c-b70d-1bb140698e1c_788x1620.png" width="788" height="1620" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/428f4954-4b32-436c-b70d-1bb140698e1c_788x1620.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:1620,&quot;width&quot;:788,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!Iz6N!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F428f4954-4b32-436c-b70d-1bb140698e1c_788x1620.png 424w, /__u/substackcdn.com/image/fetch/$s_!Iz6N!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F428f4954-4b32-436c-b70d-1bb140698e1c_788x1620.png 848w, /__u/substackcdn.com/image/fetch/$s_!Iz6N!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F428f4954-4b32-436c-b70d-1bb140698e1c_788x1620.png 1272w, /__u/substackcdn.com/image/fetch/$s_!Iz6N!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F428f4954-4b32-436c-b70d-1bb140698e1c_788x1620.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><ul><li><p><strong>Definition</strong>: Provide a business definition of the business process.</p></li><li><p><strong>Business Events</strong>. If the business process is evolving, provide a list of business events.</p></li><li><p><strong>Measured By</strong>. List how the process is measured. Obviously, these become the measures in your Fact.</p></li><li><p><strong>Related To</strong>. List the business entities that represent the who, what, where, when and why of the business process. Give a cardinality where it makes sense.</p></li><li><p><strong>Business Domain</strong>: The business domain this entity belongs too. It&#8217;s an indication of what data mart the entity will belong too. If you want to keep conformed dimensions in a Master Data Mart, then, set this value to master.</p></li><li><p><strong>Type of</strong>: If this entity is a subtype of another entity, name the other entity here.</p></li><li><p><strong>Subtypes</strong>: The list of subtypes of this entity.</p></li></ul><p>A business process will become a Fact in the Data Warehouse.</p><h3><strong>Business Entities</strong></h3><p>Below is an example of a <strong>Business Entity description</strong> in an Ontology document:</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!i8NM!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7801a660-0721-4813-a59e-5eae00f78d52_625x844.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!i8NM!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7801a660-0721-4813-a59e-5eae00f78d52_625x844.png 424w, /__u/substackcdn.com/image/fetch/$s_!i8NM!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7801a660-0721-4813-a59e-5eae00f78d52_625x844.png 848w, /__u/substackcdn.com/image/fetch/$s_!i8NM!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7801a660-0721-4813-a59e-5eae00f78d52_625x844.png 1272w, /__u/substackcdn.com/image/fetch/$s_!i8NM!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7801a660-0721-4813-a59e-5eae00f78d52_625x844.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!i8NM!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7801a660-0721-4813-a59e-5eae00f78d52_625x844.png" width="625" height="844" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/7801a660-0721-4813-a59e-5eae00f78d52_625x844.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:844,&quot;width&quot;:625,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!i8NM!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7801a660-0721-4813-a59e-5eae00f78d52_625x844.png 424w, /__u/substackcdn.com/image/fetch/$s_!i8NM!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7801a660-0721-4813-a59e-5eae00f78d52_625x844.png 848w, /__u/substackcdn.com/image/fetch/$s_!i8NM!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7801a660-0721-4813-a59e-5eae00f78d52_625x844.png 1272w, /__u/substackcdn.com/image/fetch/$s_!i8NM!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F7801a660-0721-4813-a59e-5eae00f78d52_625x844.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><ul><li><p><strong>Definition</strong>: Provide a business definition of the entity. Keep this definition relatively concise. Be careful not to wander into describing other entities and processes in the business.</p></li><li><p><strong>Attributes</strong>: Include a list of attributes of the entity. Provide example values where possible.</p></li><li><p><strong>Synonyms</strong>: Where it&#8217;s possible to identify the same entity in a source system, name the same entity as a synonym. This can help understanding, especially if you have multiple systems providing the same role.</p></li><li><p><strong>Business Domain</strong>: The business domain this entity belongs too. It&#8217;s an indication of what data mart the entity will belong too. If you want to keep conformed dimensions in a Master Data Mart, then, set this value to master.</p></li><li><p><strong>Type of</strong>: If this entity is a subtype of another entity, name the other entity here.</p></li><li><p><strong>Subtypes</strong>: The list of subtypes of this entity.</p></li></ul><p>A business entity will become a Dimension in the Data Warehouse.</p><h2><strong>Model Storming</strong></h2><p>A very similar approach, with much more detail about how you arrive at these definitions is described by Lawrence Corr in his book <a href="https://amzn.to/2rl8k12">Agile Data Warehouse Design: Collaborative Dimensional Modeling, from Whiteboard to Star Schema</a>. It is a step-by-step guide for capturing data warehousing/business intelligence (DW/BI) requirements and turning them into high-performance dimensional models in the most direct way: by model-storming (data modelling + brainstorming) with BI stakeholders. It describes BEAM&#10034;, an agile approach to <a href="https://www.dimodelo.com/blog/2024/what-is-dimensional-modeling-introduction/">dimensional modelling</a>, for improving communication between data warehouse designers, BI stakeholders and the whole DW/BI development team.</p><h2><strong>Data Driven Design</strong></h2><p>Bottom Up &#8220;Data Driven Design&#8221; is also an exercise in &#8220;Modelling Reality&#8221;.</p><p>Data Driven Design refers to a design technique that focuses on examining the data and database schema of Source Systems to understand the Business Processes and Entities of the Business. The fact is that the Business process and entities exist in the source systems, in detail.</p><p>A forensic examination of the source systems can reveal the business processes and entities.</p><p>Data Warehouse projects have certain characteristics that make them suitable for Data Driven Design. The key characteristic is that Data Warehouse projects are highly constrained. They are constrained by the data contained in the source systems of the Data Warehouse, and, from a requirements perspective, a Data Warehouse is constrained to modelling existing business processes (other than perhaps reporting and management processes).</p><p>Unlike an operational system project where development is about new or changing business processes, it is not realistic to get requirements about, for instance, what attributes of a Customer that need to be captured, and then model into a Data Warehouse Data Model. First&#8230; the underlying Source System may or may not support the attributes and secondly it is easier to go directly to the existing Source System and discover them.</p><p>Data Driven Design will shortcut the requirements process. Clearly existing Business Process will be manifest in one or more Source Systems, and can be &#8216;discovered&#8217;. Thus a Data Driven Design approach can be taken, using existing data to derive a design for the Data Warehouse. Data Driven Design doesn&#8217;t mean ignoring business requirements all together. To the contrary the business needs to be brought along on the journey, but only limited and specific input and prioritization is required from the business in the early iterations. In later iterations the business will be better equipped to properly articulate their requirement.</p><h3><strong>Overview of Data-Driven Design for Data Warehousing</strong></h3><p>Below is an outline of Data-Driven Design and Agile Methodology applied to Data Warehousing.</p><h4><strong>First Iteration</strong></h4><p>The first iteration is a little different. It is as much a business education process, as it is a development exercise. The four steps of the process are described below. They will occur in roughly this order, but it&#8217;s likely that some steps will occur simultaneously and repetitively as required.</p><ol><li><p><strong>Discover the Business Processes that are included in the project scope</strong>. Data Driven Design doesn&#8217;t mean ignoring business requirements altogether. <em>To the contrary, the business needs to be consulted constantly and brought along on the journey</em>. A detailed description of the Business Process is not required. Just a simple accurate story card for each Business Process and Business Event, identifying the key entities involved (The Who, What, Where, When and Why) and how the Business Events are measured. For example&#8230; an Ontology! The identified Business Processes need to be prioritized in a business value order. This order needs to be weighed against the technical complexity of each Business Process to decide which Business Processes will be implemented in the first iteration of the project. Try to choose a relatively high value and simple Business Processes for the first iteration.</p></li><li><p><strong>Discover the Source Systems for the selected iteration 1 Business Processes </strong>and get access to their database/files etc. Having real-life data is important, and can sometimes be a challenge.</p></li><li><p><strong>Discover within the Source System database(s) the manifestation of each of the Business Process. </strong>This will require communication back and forth with the business representatives. Think of yourself as a data detective. A forensic data detective, CSI style! Quite often Source Database tables and columns are well named and easy to understand. In many cases, the Database schema is undecipherable. Many packaged ERP suffer from this. Every Holmes needs a Watson. Collaboration with a data-focused Subject Matter Expert (SME) or experienced Source System programmer is essential. A data focused SME will have experience with the underlying data, perhaps learned from extracting data from the Source System Database for reports. This step will identify the tables, columns, data and grain of data involved in each Business Process. It should also discover various cases and examples of the Business Process within the data. Save these cases if possible, they become useful for testing later. Physically, this step will involve a lot of data profiling and querying of the Database. Other resources you will find useful are Source System user manuals, technical manuals, a data dictionary or existing reports that extract data.</p></li><li><p><strong>Develop a first cut Data Warehouse Data Model and ETL based on what has been discovered</strong>. The Data Model will contain only those tables required for the first iteration but must conform to good Data Warehouse design principles, so that the model can be easily expanded in the future. It is absolutely essential that a next generation Data Warehousing tool like <a href="https://www.dimodelo.com/index.php">Dimodelo Data Warehouse Studio</a> is used to develop the Data Warehouse and ETL. The Data Warehouse and ETL is going to go through many iterations, much change, plenty of regression testing and several releases. Short iterations are just not feasible without a tool like Dimodelo Data Warehouse Studio.</p></li></ol><p>The idea of the first iteration, and to a lesser extent, other early iterations, is to give the business a first look at the Data Warehouse. This helps to get them thinking dimensionally and improve their ability to articulate requirements. Gathering requirements is traditionally a major issue in Data Warehouse projects. The first iteration is an education process, helping the business understand the capabilities of BI. We recommend you demonstrate standard reports, dashboards, scorecards and ad-hoc analytics. Only deploy the first iteration to a sandpit environment. Somewhere the users can &#8216;play&#8217;. Keep expectations of data accuracy low, it&#8217;s unlikely you will nail the data 100%. It&#8217;s possible you may even need to start from scratch again, but that&#8217;s not an issue with Dimodelo Data Warehouse Studio or other similar tools.</p><h4><strong>Subsequent Iterations</strong></h4><p>Rinse and Repeat. Subsequent iterations follow the same process as the first iteration but the focus of subsequent iterations is to improve and refine the existing solution based on feedback from previous iterations. Only introduce new functionality for new Business Processes when resources allow.</p><p>Subsequent iterations introduce additional Agile disciplines, like Test Driven Development, Continuous Integration, Source Control and Release Management, each of which could fill several blog posts on their own. It does suffice to say, automation is the key.</p><p>It&#8217;s likely that subsequent iterations become release candidates for release into production. Again discipline is required. Releasing a Data Warehouse into production is not an easy task, especially if there is an existing version already in production. At this point, it is also important to focus on non-functional requirements like security, disaster recovery etc. Usually, the planning for non-functional requirements would have already occurred, and there is nothing wrong with that. However, where there is a fairly standard architectural scenario, there is an argument that it may not be wise to invest time and money into the architectural tasks until a viable Data Warehouse and BI solution that meets the business needs has been proved.</p><p>.. Now&#8230; if only we could get the PMO, the Op Ex and Cap Ex budgets, and the business to align with the uncertainty of an Agile project&#8230; A whole other blog post again.</p><h3><strong>The Criticism of Data Driven Design</strong></h3><p>In the past Data Driven design has been used on Data Warehouse projects to the exclusion of all other techniques, and without using an Agile project methodology or Agile Data Warehouse development tools like Dimodelo Data Warehouse Studio. User involvement was avoided or minimized (which suited IT). It was mistakenly thought that Data Warehouse development meant simply re-modelling multiple source systems into a single Data Warehouse model. Only after the system was built, using inefficient, error-prone, time consuming and inflexible manual coding practices were the users engaged properly. Unfortunately, more often than not, the results miss the mark and failed to answer the business questions. With an inflexible ETL framework that takes months to make any significant change, the project team found themselves in trouble, and potentially out of budget.</p><p>The real problem was the time the development team took to develop the solution and the inflexible nature of the resulting system. <em>Shorten the development cycles, use a <a href="https://www.dimodelo.com/">Data Warehouse Automation tool</a>, call the result a prototype, and a paradigm shift occurs</em>. Iterate multiple times to improve and refine the application to the business requirements.</p><h3><strong>Why use the Agile Methodology for Data Warehousing Projects?</strong></h3><p>Many IT projects fail. Depending on who you believe, its anywhere between 50% and 80% (See references below). Shocking! I believe that you need to take these figures with a grain of salt. It depends on your definition of failure (See discussion on failure below).</p><p>It has also been shown that small projects are more successful than large projects and those projects using the Agile methodology are also more successful (See references). Given that small agile projects are the most successful and that Gartner states that over 70% of BI projects are not successful, it follows that applying an Agile project methodology to a Data Warehouse project is a sensible strategy. Data Driven Design is a perfect companion for Agile.</p><p>Failure Rate References:</p><ul><li><p><a href="http://bivaluenomics.blogspot.com.au/2012/08/how-to-fail-your-way-to-bi-success_30.html">Gartner 70-80% of BI Projects Fail</a> and <a href="http://www.gartner.com/DisplayDocument?ref=clientFriendlyUrl&amp;id=1873915">Report</a></p></li><li><p><a href="http://www.meironke.com/2012/03/68-percent-projects-not-successful/">Standish Chaos 2009</a></p></li><li><p><a href="http://www.projectsmart.co.uk/docs/chaos-report.pdf">Standish Chaos Original</a></p></li></ul><p>Small projects are more successful than large projects references:</p><ul><li><p><a href="http://thisiswhatgoodlookslike.com/2012/06/10/gartner-survey-shows-why-projects-fail/">Gartner Survey Shows Why Projects Fail</a></p></li><li><p><a href="http://blogs.gartner.com/mark_mcdonald/2012/10/29/mckinsey-report-highlights-failure-of-large-projects-why-it-is-better-to-be-small-particularly-in-it/">Failure of large projects &#8211; why it is better to be small particularly in IT</a><br>Agile project methodology is more successful references:</p></li><li><p><a href="http://www.ambysoft.com/surveys/success2011.html">Ambysoft Project Success Rate Survey</a></p></li><li><p><a href="http://www.enterpriseappstoday.com/business-intelligence/why-most-business-intelligence-projects-fail-1.html">Agile Business Intelligence Would Be A Good Idea</a></p></li><li><p><a href="http://www.mountaingoatsoftware.com/blog/agile-succeeds-three-times-more-often-than-waterfall">Agile succeeds three times more often than Waterfall</a></p></li></ul><h4><strong>Definition of Project Failure</strong></h4><p>The definition of project failure is usually a project that has a combination of the following issues: significantly over budget, significantly over time, doesn&#8217;t deliver full functionality, or is cancelled outright. However, I think it&#8217;s more subjective than that, and depends on project context. If a Home building project went over budget 20% or time by 20%, but at the end of the project, the house was everything the client wished for&#8230; is this a failure? The answer &#8211; depends&#8230; For a more in-depth understanding of the subjective contextual nature of project failure, you can read <a href="http://www.computer.org/portal/c/document_library/get_file?uuid=984758f1-4f03-4609-afe6-1c2e4df31900&amp;groupId=889147">The rise and fall of Standish Chaos Report figures</a>.</p><h1><strong>Testing your Design</strong></h1><p>This is an essential step that will improve your design.</p><p>How do you test your design? No first cut design stands up to the appearance of a report! Designing a data warehouse to cater only for existing reports, spreadsheets and analysis is a mistake. However, you should test your design against those existing reports etc.</p><p>Can you produce those reports from your data warehouse? Inevitably the answer will be no. You will discover new calculated measures, hierarchies and different aggregations needed to respond to these requirements. You may discover you need new periodic snapshot tables or entirely different facts from different domains.</p><h1><strong>Conclusion</strong></h1><p>In my experience, the Ontology method is the most successful way of defining Data Warehouse requirements.</p><p>If you want to take this exercise even further I would recommend the Model-Storming approach. Indeed, I would highly recommend at least reading the Laurence Corr&#8217;s book. It will improve how you write an Ontology.</p><p>The Ontology exercise will most likely be informed by a Data Driven Design approach. Because your source systems are the manifestation of your business process and entities, it is likely you will discover the processes and entities you need to document through Data-Driven analysis.</p><p>Once the ontology is complete you then use it to define your Data Warehouse Matrix. This then becomes your high-level design document, project scope and key project planning and communication tool.</p><p>I highly recommend you undertake this style of requirements gathering before starting the build of your data warehouse. I see many implementations dive straight into the design of facts and dimensions. The requirements gathering exercise is the missing link between the business and the design.</p><p>I&#8217;ve seen many experienced data warehouse developers encounter an ontology document for the first time and thank God for its existence! Literally.</p><p>It need not be a long exercise. A 3-day workshop with experienced data analysts, business analysts and/or SMEs is all you need to gather the information for a reasonably complex domain, plus perhaps 2-3 days to document. This document will keep delivering value, especially as the makeup of the team changes. It may be the only definitive definition of the business processes in existence.</p>]]></content:encoded></item><item><title><![CDATA[What is a Data Warehouse (and why you need one)]]></title><description><![CDATA[A Data Warehouse is a database that supports enterprise reporting and analysis.]]></description><link>https://dimodelo.substack.com/p/what-is-a-data-warehouse-and-why-you-need-one</link><guid isPermaLink="false">https://dimodelo.substack.com/p/what-is-a-data-warehouse-and-why-you-need-one</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Mon, 26 Feb 2024 08:09:21 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/47542906-94cf-4a84-83cc-a4bc2b08d728_320x616.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>A Data Warehouse is a database that supports enterprise reporting and analysis. A well-designed data warehouse uses accepted data modelling and management techniques to provide an integrated data source that makes it easy to build reports and analyses.</p><p>A data warehouse should exhibit the following four characteristics:</p><ol><li><p><strong>Integrated</strong>. A data warehouse takes a copy of the data (on a regular basis) from the enterprise&#8217;s application systems. It integrates that data into &#8220;one place&#8221;, simplifying data access for reporting purposes. A Data warehouse doesn&#8217;t capture or create new data itself.</p></li><li><p><strong>Subject-oriented, not source system-oriented</strong>. A data warehouse reorganises the source data into business subjects/domains, making it easier for users to understand and consume.</p></li><li><p><strong>Historical/Time Variant</strong>. A Data Warehouse records the history of how data changes. This is important for accurate reporting, auditing and efficient data management.</p></li><li><p><strong>Non-Volatile</strong>. Data is loaded in periodic &#8220;batches&#8221;. The data doesn&#8217;t change from moment to moment; rather, it&#8217;s stable between load periods. This means reporting and analysis can be conducted without the data changing underneath you.</p></li></ol><p><strong>At the heart of a data warehouse is the ability to organize data so end users, report developers, data analysts and data scientists can easily consume it</strong>. What do I mean by easily consumed? First, they have a single source of trusted, modelled, easy-to-understand data. Second, users can access that source through BI tools that make it easy to create new reports and analyses or interact directly with the data via code (SQL, R, Python, etc).</p><p><strong>You need solid data architecture and modelling techniques to achieve the ideal of &#8220;easily consumable data&#8221;</strong>. The most commonly used architecture and modelling technique is the <strong>&#8220;Kimball&#8221;</strong> <strong>data warehouse</strong> <strong>methodology</strong>. The Kimball methodology describes:</p><ol><li><p>A <strong>layered data architecture</strong> typically comprised of Staging, Transformation, Presentation and Semantic layers.</p></li><li><p>A <strong><a href="https://www.dimodelo.com/blog/2024/what-is-dimensional-modeling-introduction/">Dimensional data modelling technique</a></strong> that models data in a simple, easy-to-understand &#8220;Star&#8221; schema.</p></li></ol><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!vmYx!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa0e83def-7f18-4ca4-82c3-1808f7004b39_320x616.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!vmYx!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa0e83def-7f18-4ca4-82c3-1808f7004b39_320x616.png 424w, /__u/substackcdn.com/image/fetch/$s_!vmYx!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa0e83def-7f18-4ca4-82c3-1808f7004b39_320x616.png 848w, /__u/substackcdn.com/image/fetch/$s_!vmYx!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa0e83def-7f18-4ca4-82c3-1808f7004b39_320x616.png 1272w, /__u/substackcdn.com/image/fetch/$s_!vmYx!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa0e83def-7f18-4ca4-82c3-1808f7004b39_320x616.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!vmYx!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa0e83def-7f18-4ca4-82c3-1808f7004b39_320x616.png" width="320" height="616" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/a0e83def-7f18-4ca4-82c3-1808f7004b39_320x616.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:616,&quot;width&quot;:320,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;simple data warehouse architecture&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="simple data warehouse architecture" title="simple data warehouse architecture" srcset="/__u/substackcdn.com/image/fetch/$s_!vmYx!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa0e83def-7f18-4ca4-82c3-1808f7004b39_320x616.png 424w, /__u/substackcdn.com/image/fetch/$s_!vmYx!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa0e83def-7f18-4ca4-82c3-1808f7004b39_320x616.png 848w, /__u/substackcdn.com/image/fetch/$s_!vmYx!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa0e83def-7f18-4ca4-82c3-1808f7004b39_320x616.png 1272w, /__u/substackcdn.com/image/fetch/$s_!vmYx!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa0e83def-7f18-4ca4-82c3-1808f7004b39_320x616.png 1456w" sizes="100vw" fetchpriority="high"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><ul><li><p>Data from multiple systems is landed in the <strong>staging layer</strong>. It implements the first &#8220;integration&#8221; characteristic described above, i.e., simply having all your data &#8220;in one place.&#8221; A persistent staging layer is a common variant that also captures the history of change, implementing the third &#8220;historical&#8221; characteristic.</p></li><li><p>The<strong> transformation layer</strong> is where data begins its journey into a subject-orientated format (the second characteristic). Transformation can be complex, and the transformation layer is where this complexity is implemented. It also supports the reuse of the logic by the presentation layer. In this layer, data from multiple systems is often matched and merged into subject area entities.</p></li><li><p>The<strong> presentation layer</strong> is the final subject-orientated representation of the data (the second subject-orientated characteristic). It is modelled using a strict <strong>&#8220;star&#8221; schema</strong>. The <a href="https://www.dimodelo.com/blog/2024/what-is-a-star-schema-and-why-its-important/">Star Schema</a> is an easy-to-understand data model that is easy to navigate and supports multiple analytic use cases. The Star schema is comprised of <a href="https://www.dimodelo.com/blog/2024/dimension-tables-an-introduction/">Dimensions</a> and <a href="https://www.dimodelo.com/blog/2024/what-is-a-fact-table-and-why-you-need-them/">Facts</a> and their relationships.</p></li><li><p>Typically, the <strong>semantic layer</strong> is the layer exposed to end users. End users interact with the <a href="https://www.dimodelo.com/blog/2023/what-is-a-semantic-layer-what-why-how-and-more/">semantic layer</a> for data analysis and visualization via BI tools like PowerBI or Tableau. A semantic layer is implemented in a technology that facilitates high-performance aggregated queries over large amounts of data. The semantic layer&#8217;s data model mirrors the presentation layer&#8217;s Star schema. It further augments the data model with calculated measures that can&#8217;t be created in other technologies. More advanced users like data scientists and advanced data analysts may be granted access to the presentation of transformation layers as needed.</p></li><li><p><strong>Extract, Transform, Load (ETL)</strong>. ETL is not a layer but rather the logic that moves data between layers. The ETL code extracts data from the source, transforms it into a Star schema, and loads it into the presentation layer. ETL is usually executed periodically (daily, weekly, four hourly, etc.) and loads batches of data that have changed in that period. It implements the &#8220;non-volatile&#8221; characteristic.</p></li></ul><p>An alternate architecture growing in popularity is the <strong>data lakehouse</strong>. A data lakehouse is a combination of the data lake and data warehouse architectures. The data lakehouse describes Bronze, Silver and Gold layers that correspond to the Staging, Transform and Presentation layers of the Kimball Data Warehouse architecture. This is a vendor lead (Databricks) reimagining of the data warehouse implemented on different technologies. Data warehouses have traditionally been developed using database technology, whereas the data lakehouse is born out of the open source big data, file system based (HDFS), and Spark ETL technologies that Databricks have commercialized.</p><h2>Why you need a Data Warehouse</h2><p>The universal truths of data in every organisation I&#8217;ve worked in are:</p><ol><li><p>Data is messy!</p></li><li><p>Someone, somewhere, somehow needs to deal with the mess.</p></li><li><p>The best place to deal with the mess is in a centralized data warehouse rather than over hundreds of disparate reports.</p></li></ol><p>The best way to understand the benefits of a data warehouse is to imagine your life as a report developer without one.</p><ol><li><p>First, your data is spread across multiple systems, most of which you cannot access.</p></li><li><p>Second, the data quality is poor. It&#8217;s incomplete, inaccurate, contradictory and not up to date.</p></li><li><p>Third, you need to mix, match, and merge that data with data from other systems. There may not be an obvious or easy way to do that.</p></li><li><p>Fourth, the volume of data you need for your report is massive, and the source systems cannot or will not cope with your query.</p></li><li><p>Fifth, the source system doesn&#8217;t keep a history of data change, so the reports unexpectedly change for end users.</p></li><li><p>Lastly, you use some logic in your report that doesn&#8217;t match the logic of someone else&#8217;s report, so end users are using and comparing results that don&#8217;t match across reports.</p></li></ol><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!uBir!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F121f300c-df47-4623-89af-afdb8224a2d4_1173x617.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!uBir!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F121f300c-df47-4623-89af-afdb8224a2d4_1173x617.png 424w, /__u/substackcdn.com/image/fetch/$s_!uBir!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F121f300c-df47-4623-89af-afdb8224a2d4_1173x617.png 848w, /__u/substackcdn.com/image/fetch/$s_!uBir!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F121f300c-df47-4623-89af-afdb8224a2d4_1173x617.png 1272w, /__u/substackcdn.com/image/fetch/$s_!uBir!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F121f300c-df47-4623-89af-afdb8224a2d4_1173x617.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!uBir!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F121f300c-df47-4623-89af-afdb8224a2d4_1173x617.png" width="1173" height="617" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/121f300c-df47-4623-89af-afdb8224a2d4_1173x617.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:617,&quot;width&quot;:1173,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;Your Data&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="Your Data" title="Your Data" srcset="/__u/substackcdn.com/image/fetch/$s_!uBir!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F121f300c-df47-4623-89af-afdb8224a2d4_1173x617.png 424w, /__u/substackcdn.com/image/fetch/$s_!uBir!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F121f300c-df47-4623-89af-afdb8224a2d4_1173x617.png 848w, /__u/substackcdn.com/image/fetch/$s_!uBir!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F121f300c-df47-4623-89af-afdb8224a2d4_1173x617.png 1272w, /__u/substackcdn.com/image/fetch/$s_!uBir!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F121f300c-df47-4623-89af-afdb8224a2d4_1173x617.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>Imagine a bunch of developers all creating reports and analyses and solving the same data problems over and over again. This would very quickly result in a chaotic and unmaintainable mess.</p><p>The situation above is what inspired the development of the data warehouse concept.</p><p><strong>The benefits of a data warehouse include:</strong></p><ul><li><p><strong>Integrating data from multiple sources</strong> into a single data store provides easy access to data across business domains, such as financial, HR, operations, and sales.</p></li><li><p>Ability to model data to make it <strong>easy to consume. </strong>By modelling data in an integrated subject-orientated, easy-to-navigate star schema, data becomes much easier for end users to work with and consume. This leads to the next point &#8211; end-user productivity.</p></li><li><p><strong>End-User Productivity. </strong>In any organization, a subset of people spend part or all of their day producing information in one form or another<strong>.</strong> Typically, they spend much of their time wrangling messy data. One of the benefits of a data warehouse is end-user productivity. All that data manipulation is already done, and the users can concentrate on analysing and responding to information rather than producing it.</p></li><li><p><strong>A single version of the truth</strong>. A data warehouse lets you implement the logic for metrics once and then have all reports and analyses use the data warehouse as their source. That way, there is just a &#8220;single version of the truth&#8221;. Business users work with agreed definitions for KPIs, metrics and measures.</p></li><li><p>A Data Warehouse is a sustainable solution that <strong>copes well with underlying change</strong>. The Transform/Presentation layer has its own business-focused model that doesn&#8217;t use source system schema or language. This delivers a level of abstraction between data sources and reports. This means that even if the data source changes (which happens constantly!), the business-focused model can remain the same, and reports that depend on that model can remain untouched. The new source does need to be &#8220;plugged into&#8221; the business-focused model, which can be done with little impact on reports.</p></li><li><p><strong>Remove load from operational systems</strong>. Operational systems are generally tuned to manage hundreds, if not thousands, of small individual transactions. Analytics can require querying millions (even billions) of rows. For example, a total annual sales metric for a large e-commerce platform requires summing across all sales rows in a year. A single analytical query can cause major performance issues for an operational system. Separating reporting and analysis load to a data warehouse removes adverse impacts on operational systems.</p></li><li><p><strong>Analyze the past as it existed in the past</strong>. For example, imagine a salesperson (let&#8217;s call him Gary) works in region A. A regional sales report rolls up the sales figures for Jane into the total for region A. Imagine Jane moving from Region A to Region B. In the report, Jane&#8217;s past sales suddenly moved from Region A to Region B, which was undesirable. A Data Warehouse has modelling methods to prevent this issue. In a data warehouse, historical sales would remain associated with Region A, and only new sales would be attributed to Region B.</p></li><li><p><strong>Eliminate Personnel Risk</strong>. Business logic is often locked up in spreadsheets or visualizations (Power BI, Tableau, Qlik, etc.) created and managed by individuals. There is a risk that if that individual leaves, no one else is able to manage these sometimes business-critical spreadsheets or reports. Centralizing your business logic (measures, KPIs, etc.) managed by a data warehouse team reduces this risk.</p></li><li><p><strong>Data augmentation for reporting purposes</strong>. A Data Warehouse can model and augment data specifically for reporting purposes. This augmentation isn&#8217;t available in a source system. For example, analytics functions like relative period (e.g., MTD, YTD, etc.), periodic and rolling calendars (e.g., Christmas Period, Public holidays, etc.), the definition of acceptable ranges, targets, KPIs, data aggregation or disaggregation, and periodic balances (e.g., end-of-month balances).</p></li><li><p><strong>Keep historical data</strong>. A data warehouse can capture the history of how data changes. This can assist with accurate data reporting and auditing and improve load performance. A Data Warehouse can keep historical data beyond the normal&nbsp;<strong>retention period</strong>&nbsp;of operational systems.</p></li></ul>]]></content:encoded></item><item><title><![CDATA[Designing an Enterprise Data Warehouse – where to start?]]></title><description><![CDATA[When faced with a new Enterprise Data Warehouse development, it&#8217;s hard to know where to start.]]></description><link>https://dimodelo.substack.com/p/designing-an-enterprise-data-warehouse-where-to-start</link><guid isPermaLink="false">https://dimodelo.substack.com/p/designing-an-enterprise-data-warehouse-where-to-start</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Wed, 22 Nov 2023 05:28:38 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/b8d91a1e-922f-4875-aaac-8408cb3cea63_800x510.jpeg" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>When faced with a new Enterprise Data Warehouse development, it&#8217;s hard to know where to start. Many people make the mistake of starting with some reporting requirements. Unfortunately, this leads to narrow silos that can&#8217;t accommodate new requirements. Initially, it&#8217;s better to anchor your high-level design to the core business processes of the business. If you do this, you will meet 80% of your reporting requirements without ever seeing them!</p><p>To align your Data Warehouse with the strategy, objectives and core processes of the business, you first need to understand the concept of the Organizational &#8220;Value Chain&#8221; and how this leads to Business modelling and Data Warehouse design. This ultimately feeds back into strategic decision-making.</p><p>Understanding the Organization&#8217;s Value Chain and conducting Business modelling to define the Data Warehouse design massively enhances the value derived from Reporting and Analysis.</p><h2>Organization Value Chain</h2><p>What is an Organizational Value Chain?</p><p>Organizational &#8220;Value Chains&#8221; were first introduced by Michael Porter in his book &#8220;<a href="https://www.amazon.com/Competitive-Advantage-Creating-Sustaining-Performance/dp/0684841460/ref=sr_1_1?crid=1LDMC16VZZRYD">Competitive Advantage</a>&#8220;.</p><p>A value chain is a set of connected activities an organization carries out to create value (i.e., products and services) for its customers. The value created for the customer should be greater than the cost of production, and the result is the margin. A value chain is a systematic way of examining these internal activities and how they interact to enhance customer value, margin and competitive advantage.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!cnYQ!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a5c645e-9bf6-4dc8-93ef-55255d398ed5_800x510.jpeg" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!cnYQ!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a5c645e-9bf6-4dc8-93ef-55255d398ed5_800x510.jpeg 424w, /__u/substackcdn.com/image/fetch/$s_!cnYQ!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a5c645e-9bf6-4dc8-93ef-55255d398ed5_800x510.jpeg 848w, /__u/substackcdn.com/image/fetch/$s_!cnYQ!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a5c645e-9bf6-4dc8-93ef-55255d398ed5_800x510.jpeg 1272w, /__u/substackcdn.com/image/fetch/$s_!cnYQ!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a5c645e-9bf6-4dc8-93ef-55255d398ed5_800x510.jpeg 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!cnYQ!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a5c645e-9bf6-4dc8-93ef-55255d398ed5_800x510.jpeg" width="800" height="510" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/3a5c645e-9bf6-4dc8-93ef-55255d398ed5_800x510.jpeg&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:510,&quot;width&quot;:800,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!cnYQ!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a5c645e-9bf6-4dc8-93ef-55255d398ed5_800x510.jpeg 424w, /__u/substackcdn.com/image/fetch/$s_!cnYQ!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a5c645e-9bf6-4dc8-93ef-55255d398ed5_800x510.jpeg 848w, /__u/substackcdn.com/image/fetch/$s_!cnYQ!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a5c645e-9bf6-4dc8-93ef-55255d398ed5_800x510.jpeg 1272w, /__u/substackcdn.com/image/fetch/$s_!cnYQ!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3a5c645e-9bf6-4dc8-93ef-55255d398ed5_800x510.jpeg 1456w" sizes="100vw" fetchpriority="high"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Value Chain Analysis</figcaption></figure></div><p>Porter divided his activities into the following:</p><ul><li><p><strong>Primary activities</strong>. Primary activities are related directly to the production, distribution and sale, maintenance and support of products or services.</p></li><li><p><strong>Support activities</strong>. These activities support the primary functions above, E.g. Procurement, Human Resources, IT, Accounting, Legal, Administration, etc.</p></li></ul><p>By understanding the collection of primary and supporting activities, a data warehouse designer can start to form a view of the data warehouse that aligns with the activities and strategic goals of the business.</p><p>To learn more about the Value Chain, I recommend watching this video &#8211; &nbsp;<a href="https://www.youtube.com/watch?v=SI5lYaZaUlg&amp;t=916s">Value Chain Analysis EXPLAINED | B2U | Business To You &#8211; YouTube</a>.</p><h2>Business Modelling</h2><p>&#8220;Business Modeling&#8221; describes the process of capturing details of the Organizational Value Chain in a format appropriate for Data Warehousing. The actual Data Warehouse &#8220;design&#8221; work happens in this process.</p><p><strong>What is Business modelling?</strong>&nbsp;&#8211; &#8220;The act of describing the properties and relationships of a set of business activities and the business entities involved in the business activities.&#8221;</p><ul><li><p><strong>Business activities</strong>: The primary and supporting activities identified in the Organizational Value Chain.</p></li><li><p><strong>Business entities:</strong>&nbsp;The &#8220;who&#8221;, &#8220;what&#8221;, &#8220;where&#8221;, &#8220;when&#8221;, and &#8220;why&#8221; that participate in or are produced by the activities.</p></li></ul><p>The Business Modeler must distinguish between business activities and business entities. This distinction is key to success. In later sections, you discover that business activities become one or more Facts in the data warehouse, and Business Entities become <a href="/__u/dimodelo.substack.com/p/dimension-tables-an-introduction/">Dimensions</a>.</p><p>The Business Model also serves to identify the integration of business activities across business entities, I.e., the business entities used in common across activities. These common entities become the conformed dimensions of the Data Warehouse.</p><p>The Business Model also provides a common language to the business. It becomes the basis of a Business Glossary or Data Dictionary.</p><h2>Use a Data Warehouse Bus Matrix to capture the business model</h2><p>You can use a <a href="/__u/dimodelo.substack.com/p/what-is-a-data-warehouse-bus-matrix-and-why-you-need-one/">Data Warehouse Matrix</a> to capture and communicate the Business Model at a high level.</p><p>A &#8220;Data Warehouse Bus Matrix&#8221; describes the high-level design of a Data Warehouse. At a glance, it shows all the facts and dimensions of a data warehouse and their relationships in a table-like &#8216;matrix&#8217;.</p><p>for example:</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!rwMH!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa5116cd9-39e8-4825-ac5b-8cc448f5997c_697x374.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!rwMH!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa5116cd9-39e8-4825-ac5b-8cc448f5997c_697x374.png 424w, /__u/substackcdn.com/image/fetch/$s_!rwMH!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa5116cd9-39e8-4825-ac5b-8cc448f5997c_697x374.png 848w, /__u/substackcdn.com/image/fetch/$s_!rwMH!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa5116cd9-39e8-4825-ac5b-8cc448f5997c_697x374.png 1272w, /__u/substackcdn.com/image/fetch/$s_!rwMH!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa5116cd9-39e8-4825-ac5b-8cc448f5997c_697x374.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!rwMH!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa5116cd9-39e8-4825-ac5b-8cc448f5997c_697x374.png" width="697" height="374" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/a5116cd9-39e8-4825-ac5b-8cc448f5997c_697x374.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:374,&quot;width&quot;:697,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!rwMH!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa5116cd9-39e8-4825-ac5b-8cc448f5997c_697x374.png 424w, /__u/substackcdn.com/image/fetch/$s_!rwMH!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa5116cd9-39e8-4825-ac5b-8cc448f5997c_697x374.png 848w, /__u/substackcdn.com/image/fetch/$s_!rwMH!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa5116cd9-39e8-4825-ac5b-8cc448f5997c_697x374.png 1272w, /__u/substackcdn.com/image/fetch/$s_!rwMH!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa5116cd9-39e8-4825-ac5b-8cc448f5997c_697x374.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>The Data Warehouse Bus Matrix is a vital tool for documenting the design of the data warehouse, the value chain activities it covers, and their relationships with Business entities. It can quickly communicate the value chain coverage, scope, status and high-level design to stakeholders, developers and end-users.</p><p><a href="/__u/dimodelo.substack.com/p/data-warehouse-bus-matrix-template/">Grab your free Data Warehouse Bus matrix template -&gt;</a></p><p>&#8220;I&#8217;ve used this Bus Matrix spreadsheet on all my projects to help design, plan and estimate data warehouses and communicate the scope and progress to stakeholders.&#8221;</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!fCY7!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffbf065b5-760e-4ce5-8687-5837c1993f5f_1082x770.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!fCY7!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffbf065b5-760e-4ce5-8687-5837c1993f5f_1082x770.png 424w, /__u/substackcdn.com/image/fetch/$s_!fCY7!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffbf065b5-760e-4ce5-8687-5837c1993f5f_1082x770.png 848w, /__u/substackcdn.com/image/fetch/$s_!fCY7!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffbf065b5-760e-4ce5-8687-5837c1993f5f_1082x770.png 1272w, /__u/substackcdn.com/image/fetch/$s_!fCY7!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffbf065b5-760e-4ce5-8687-5837c1993f5f_1082x770.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!fCY7!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffbf065b5-760e-4ce5-8687-5837c1993f5f_1082x770.png" width="1082" height="770" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/fbf065b5-760e-4ce5-8687-5837c1993f5f_1082x770.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:770,&quot;width&quot;:1082,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;Kimball Data Warehouse Bus Matrix Excel Template&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="Kimball Data Warehouse Bus Matrix Excel Template" title="Kimball Data Warehouse Bus Matrix Excel Template" srcset="/__u/substackcdn.com/image/fetch/$s_!fCY7!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffbf065b5-760e-4ce5-8687-5837c1993f5f_1082x770.png 424w, /__u/substackcdn.com/image/fetch/$s_!fCY7!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffbf065b5-760e-4ce5-8687-5837c1993f5f_1082x770.png 848w, /__u/substackcdn.com/image/fetch/$s_!fCY7!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffbf065b5-760e-4ce5-8687-5837c1993f5f_1082x770.png 1272w, /__u/substackcdn.com/image/fetch/$s_!fCY7!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffbf065b5-760e-4ce5-8687-5837c1993f5f_1082x770.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><h2>The feedback loop between the Value Chain, Business Modeling and the Data Warehouse</h2><p>If executed correctly, there is a circular relationship between aligning your data warehouse with the value chain and the feedback from the data warehouse into value chain strategic decision-making.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!4L-c!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F02280d81-670b-4aa0-ba1f-fe0427274de1_1980x1160.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!4L-c!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F02280d81-670b-4aa0-ba1f-fe0427274de1_1980x1160.png 424w, /__u/substackcdn.com/image/fetch/$s_!4L-c!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F02280d81-670b-4aa0-ba1f-fe0427274de1_1980x1160.png 848w, /__u/substackcdn.com/image/fetch/$s_!4L-c!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F02280d81-670b-4aa0-ba1f-fe0427274de1_1980x1160.png 1272w, /__u/substackcdn.com/image/fetch/$s_!4L-c!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F02280d81-670b-4aa0-ba1f-fe0427274de1_1980x1160.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!4L-c!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F02280d81-670b-4aa0-ba1f-fe0427274de1_1980x1160.png" width="1980" height="1160" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/02280d81-670b-4aa0-ba1f-fe0427274de1_1980x1160.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:1160,&quot;width&quot;:1980,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!4L-c!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F02280d81-670b-4aa0-ba1f-fe0427274de1_1980x1160.png 424w, /__u/substackcdn.com/image/fetch/$s_!4L-c!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F02280d81-670b-4aa0-ba1f-fe0427274de1_1980x1160.png 848w, /__u/substackcdn.com/image/fetch/$s_!4L-c!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F02280d81-670b-4aa0-ba1f-fe0427274de1_1980x1160.png 1272w, /__u/substackcdn.com/image/fetch/$s_!4L-c!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F02280d81-670b-4aa0-ba1f-fe0427274de1_1980x1160.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><ol><li><p>The Value Chain drives the Business Model.</p></li><li><p>The Business Model defines the Data Warehouse design.</p></li><li><p>The Data Warehouse Matrix captures the Data Warehouse design.</p></li><li><p>Reports and Analysis source their data from the Data Warehouse.</p></li><li><p>Insights and Analysis feedback into strategic decisions about the value chain, increasing customer value, margin and competitive advantage.</p></li></ol><p>The objective is Reports and Analysis that reflect the Value Chain, Business Model and Data Warehouse design, aligning reporting to business goals and delivering data and analysis that feeds directly into strategic decision-making.</p><p>Importantly, the common business language permeates at every stage, driven by the Value Chain and Business Model.</p>]]></content:encoded></item><item><title><![CDATA[How to prioritize Data Warehouse development]]></title><description><![CDATA[Today&#8217;s agile development process demands that the tasks be broken down into smaller iterative phases that incrementally deliver value. This means you need to prioritize your Data Warehouse developmen]]></description><link>https://dimodelo.substack.com/p/how-to-prioritize-data-warehouse-development</link><guid isPermaLink="false">https://dimodelo.substack.com/p/how-to-prioritize-data-warehouse-development</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Tue, 21 Nov 2023 07:35:18 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/9c11287d-ec32-463f-82c2-3ca24b1416e5_697x374.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>Attempting to deliver your Data Warehouse in a single iteration, &#8220;waterfall&#8221; style, would be very difficult. Today&#8217;s agile development process demands that the tasks be broken down into smaller iterative phases that incrementally deliver value. This means you need to prioritize your Data Warehouse development.</p><p>In the case of a Data Warehouse, the business value is provided when a Fact is delivered with at least a subset of its associated Dimensions. Decisions about which Facts and Dimensions to prioritize are complex. Below are some of the steps you can use to arrive at these decisions:</p><ol><li><p><strong>First, identify high-value dimensions</strong>. High-value dimensions are those shared by many Facts. In the example below, the high-value dimensions include Product, Staff and Calendar. By concentrating on high-value Dimensions, iterative delivery has a cumulative effect.</p></li><li><p><strong>Second, identify Fact/Business Processes that utilize the high-value dimensions.</strong></p></li><li><p><strong>Third, rank these Facts by their business value vs development complexity</strong>. High business value, low complexity Facts that utilize high-value dimensions are ideal candidates.</p></li></ol><h2>Example Prioritization</h2><p>Take the Data Warehouse shown below in a <a href="/__u/dimodelo.substack.com/p/what-is-a-data-warehouse-bus-matrix-and-why-you-need-one/">Data Warehouse Bus matrix</a>.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!a8Ys!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1e24e361-c357-401b-9ad0-abfe6a668d16_697x374.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!a8Ys!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1e24e361-c357-401b-9ad0-abfe6a668d16_697x374.png 424w, /__u/substackcdn.com/image/fetch/$s_!a8Ys!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1e24e361-c357-401b-9ad0-abfe6a668d16_697x374.png 848w, /__u/substackcdn.com/image/fetch/$s_!a8Ys!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1e24e361-c357-401b-9ad0-abfe6a668d16_697x374.png 1272w, /__u/substackcdn.com/image/fetch/$s_!a8Ys!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1e24e361-c357-401b-9ad0-abfe6a668d16_697x374.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!a8Ys!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1e24e361-c357-401b-9ad0-abfe6a668d16_697x374.png" width="697" height="374" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/1e24e361-c357-401b-9ad0-abfe6a668d16_697x374.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:374,&quot;width&quot;:697,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!a8Ys!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1e24e361-c357-401b-9ad0-abfe6a668d16_697x374.png 424w, /__u/substackcdn.com/image/fetch/$s_!a8Ys!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1e24e361-c357-401b-9ad0-abfe6a668d16_697x374.png 848w, /__u/substackcdn.com/image/fetch/$s_!a8Ys!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1e24e361-c357-401b-9ad0-abfe6a668d16_697x374.png 1272w, /__u/substackcdn.com/image/fetch/$s_!a8Ys!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1e24e361-c357-401b-9ad0-abfe6a668d16_697x374.png 1456w" sizes="100vw" fetchpriority="high"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>To decide which Fact to deliver in the first project iteration, we did the following:</p><ol><li><p>First, identified the high-value Dimensions as the Calendar, Staff and Product Dimensions. At least 3 facts share them.</p></li><li><p>Identified that the Product and Sales facts use all these high-value dimensions.</p></li><li><p>Determined the build priority based on complexity. The Production and Sales facts are both considered complex. However, the Sales fact has more dimensions; therefore, the Production fact costs less to deliver. Delivering the Production Fact first provides a cumulative development benefit. This benefit is realized when you deliver the Sales Fact in a subsequent iteration. The Sales Fact only requires the delivery of an additional three dimensions. I.e., By delivering the Production fact, you have already partially delivered the Sales fact.</p></li></ol><p>A Data Warehouse Matrix provides a framework for overall delivery that can be decomposed into rational development sprints that conform to an overall design.</p><p><a href="/__u/dimodelo.substack.com/p/data-warehouse-bus-matrix-template/">Grab your free Data Warehouse Bus matrix template -&gt;</a></p><p>&#8220;I&#8217;ve used this Bus Matrix spreadsheet on all my projects to help design, plan and estimate data warehouses and communicate the scope and progress to stakeholders.&#8221;</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!Z1Ee!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F51a3b514-5cc3-4bb1-89c6-ffc23d24ee1f_1082x770.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!Z1Ee!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F51a3b514-5cc3-4bb1-89c6-ffc23d24ee1f_1082x770.png 424w, /__u/substackcdn.com/image/fetch/$s_!Z1Ee!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F51a3b514-5cc3-4bb1-89c6-ffc23d24ee1f_1082x770.png 848w, /__u/substackcdn.com/image/fetch/$s_!Z1Ee!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F51a3b514-5cc3-4bb1-89c6-ffc23d24ee1f_1082x770.png 1272w, /__u/substackcdn.com/image/fetch/$s_!Z1Ee!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F51a3b514-5cc3-4bb1-89c6-ffc23d24ee1f_1082x770.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!Z1Ee!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F51a3b514-5cc3-4bb1-89c6-ffc23d24ee1f_1082x770.png" width="1082" height="770" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/51a3b514-5cc3-4bb1-89c6-ffc23d24ee1f_1082x770.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:770,&quot;width&quot;:1082,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;Kimball Data Warehouse Bus Matrix Excel Template&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="Kimball Data Warehouse Bus Matrix Excel Template" title="Kimball Data Warehouse Bus Matrix Excel Template" srcset="/__u/substackcdn.com/image/fetch/$s_!Z1Ee!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F51a3b514-5cc3-4bb1-89c6-ffc23d24ee1f_1082x770.png 424w, /__u/substackcdn.com/image/fetch/$s_!Z1Ee!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F51a3b514-5cc3-4bb1-89c6-ffc23d24ee1f_1082x770.png 848w, /__u/substackcdn.com/image/fetch/$s_!Z1Ee!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F51a3b514-5cc3-4bb1-89c6-ffc23d24ee1f_1082x770.png 1272w, /__u/substackcdn.com/image/fetch/$s_!Z1Ee!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F51a3b514-5cc3-4bb1-89c6-ffc23d24ee1f_1082x770.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><h3>Measuring Business Value and Complexity</h3><p>It&#8217;s essential to engage the business in determining each of the Fact&#8217;s business value and priority. For better or worse, the business usually derives business value only from the perceived value of a narrow set of reports the Fact supports. Competing interests between different business functions are inevitable and challenging, to say the least. The cumulative benefit of delivering high-value dimensions can help business users understand that delivering on other users&#8217; priorities also moves the needle closer to their requirements.</p><p>Designers measure the complexity of Facts in several ways:</p><ul><li><p>The number of dimensions associated with the Fact.</p></li><li><p>The number of source systems and source tables required to load the Fact.</p></li><li><p>The data format of the source system.</p></li><li><p>The data quality of the source system.</p></li><li><p>The accessibility of the source system.</p></li><li><p>The complexity of the transformation logic.</p></li><li><p>The number of measures in the Fact.</p></li><li><p>The type of Fact (accumulating/transaction/periodic).</p></li></ul><p>Designers measure the complexity of Dimensions in the same way with a couple of additions.</p><ul><li><p>The number of attributes in the Dimension.</p></li><li><p>The number of Type 2 attributes on the Dimension.</p></li></ul><p>To help with this prioritization, I use an enhancement to the Data Warehouse Matrix.</p><p>In the image below, I have added a measure of complexity to each of the Dimensions and Facts.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!OaVm!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2701c56f-f3f8-4f73-b8dd-27ef3942e979_697x374.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!OaVm!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2701c56f-f3f8-4f73-b8dd-27ef3942e979_697x374.png 424w, /__u/substackcdn.com/image/fetch/$s_!OaVm!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2701c56f-f3f8-4f73-b8dd-27ef3942e979_697x374.png 848w, /__u/substackcdn.com/image/fetch/$s_!OaVm!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2701c56f-f3f8-4f73-b8dd-27ef3942e979_697x374.png 1272w, /__u/substackcdn.com/image/fetch/$s_!OaVm!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2701c56f-f3f8-4f73-b8dd-27ef3942e979_697x374.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!OaVm!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2701c56f-f3f8-4f73-b8dd-27ef3942e979_697x374.png" width="697" height="374" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/2701c56f-f3f8-4f73-b8dd-27ef3942e979_697x374.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:374,&quot;width&quot;:697,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!OaVm!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2701c56f-f3f8-4f73-b8dd-27ef3942e979_697x374.png 424w, /__u/substackcdn.com/image/fetch/$s_!OaVm!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2701c56f-f3f8-4f73-b8dd-27ef3942e979_697x374.png 848w, /__u/substackcdn.com/image/fetch/$s_!OaVm!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2701c56f-f3f8-4f73-b8dd-27ef3942e979_697x374.png 1272w, /__u/substackcdn.com/image/fetch/$s_!OaVm!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2701c56f-f3f8-4f73-b8dd-27ef3942e979_697x374.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>This simple enhancement helps in the prioritization process. It also feeds into the estimation process discussed in a later post.</p><p>Shown below is a 4-level complexity scale that usually suffices:</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!vF9B!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6b08b672-132c-4322-b6ee-6a2afc5670b4_602x327.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!vF9B!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6b08b672-132c-4322-b6ee-6a2afc5670b4_602x327.png 424w, /__u/substackcdn.com/image/fetch/$s_!vF9B!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6b08b672-132c-4322-b6ee-6a2afc5670b4_602x327.png 848w, /__u/substackcdn.com/image/fetch/$s_!vF9B!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6b08b672-132c-4322-b6ee-6a2afc5670b4_602x327.png 1272w, /__u/substackcdn.com/image/fetch/$s_!vF9B!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6b08b672-132c-4322-b6ee-6a2afc5670b4_602x327.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!vF9B!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6b08b672-132c-4322-b6ee-6a2afc5670b4_602x327.png" width="602" height="327" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/6b08b672-132c-4322-b6ee-6a2afc5670b4_602x327.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:327,&quot;width&quot;:602,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!vF9B!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6b08b672-132c-4322-b6ee-6a2afc5670b4_602x327.png 424w, /__u/substackcdn.com/image/fetch/$s_!vF9B!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6b08b672-132c-4322-b6ee-6a2afc5670b4_602x327.png 848w, /__u/substackcdn.com/image/fetch/$s_!vF9B!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6b08b672-132c-4322-b6ee-6a2afc5670b4_602x327.png 1272w, /__u/substackcdn.com/image/fetch/$s_!vF9B!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6b08b672-132c-4322-b6ee-6a2afc5670b4_602x327.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><h2>Balancing value, complexity and delivery</h2><p>There is a complex interplay between business value, complexity, and cumulative delivery. Designers need to consider all these factors when planning iterations. Due to the cumulative nature of the Data Warehouse delivery, the complexity of delivering any given fact may change over time. For example, in a given iteration, you may have staged the required source data or delivered &#190; of the related Dimensions, which makes some of the remaining Facts less complex. Also, the business value of any Fact may increase relative to the remaining facts. Designers can take advantage of the cumulative delivery and plan a series of iterations to provide the most value quickly. Essentially, if you deliver &#8220;Fact A&#8221;, delivering &#8220;Fact B&#8221; becomes more straightforward.</p><p>One of the phenomena experienced when delivering a Data Warehouse is that early Facts and Dimensions appear to take significant effort and are more costly without providing a lot of value. Development tends to accelerate as more of the Data Warehouse is built. It can be a struggle getting over this low-value, high-cost &#8220;hump&#8221;, with the business becoming despondent and taking shortcuts. Understanding and communicating progress, value and complexity via the Data Warehouse Matrix can help mitigate this issue.</p>]]></content:encoded></item><item><title><![CDATA[What is a Data Warehouse Bus Matrix? (and why you need one)]]></title><description><![CDATA[A &#8220;Data Warehouse Bus Matrix&#8221; describes the high-level design of a Data Warehouse. At a glance, it shows all the facts and dimensions of a data warehouse and their relationships in a table-like &#8216;matri]]></description><link>https://dimodelo.substack.com/p/what-is-a-data-warehouse-bus-matrix-and-why-you-need-one</link><guid isPermaLink="false">https://dimodelo.substack.com/p/what-is-a-data-warehouse-bus-matrix-and-why-you-need-one</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Mon, 20 Nov 2023 11:27:52 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/75195e1c-5299-49a7-be04-35502e46eb74_697x374.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>A &#8220;Data Warehouse Bus Matrix&#8221; describes the high-level design of a Data Warehouse. At a glance, it shows all the facts and dimensions of a data warehouse and their relationships in a table-like &#8216;matrix&#8217;. It&#8217;s useful as a tool to design, plan, estimate and communicate your data warehouse.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!y5qP!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2e208213-62b5-49d8-8db2-6a436020e615_697x374.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!y5qP!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2e208213-62b5-49d8-8db2-6a436020e615_697x374.png 424w, /__u/substackcdn.com/image/fetch/$s_!y5qP!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2e208213-62b5-49d8-8db2-6a436020e615_697x374.png 848w, /__u/substackcdn.com/image/fetch/$s_!y5qP!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2e208213-62b5-49d8-8db2-6a436020e615_697x374.png 1272w, /__u/substackcdn.com/image/fetch/$s_!y5qP!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2e208213-62b5-49d8-8db2-6a436020e615_697x374.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!y5qP!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2e208213-62b5-49d8-8db2-6a436020e615_697x374.png" width="697" height="374" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/2e208213-62b5-49d8-8db2-6a436020e615_697x374.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:374,&quot;width&quot;:697,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!y5qP!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2e208213-62b5-49d8-8db2-6a436020e615_697x374.png 424w, /__u/substackcdn.com/image/fetch/$s_!y5qP!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2e208213-62b5-49d8-8db2-6a436020e615_697x374.png 848w, /__u/substackcdn.com/image/fetch/$s_!y5qP!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2e208213-62b5-49d8-8db2-6a436020e615_697x374.png 1272w, /__u/substackcdn.com/image/fetch/$s_!y5qP!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2e208213-62b5-49d8-8db2-6a436020e615_697x374.png 1456w" sizes="100vw" fetchpriority="high"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>The &#8220;Data Warehouse Matrix&#8221; comes from the industry-accepted Kimball Data Warehouse methodology. In the Kimball method, practitioners are encouraged to create a &#8220;Data Warehouse Bus Matrix&#8221; to describe the high-level design of the Data Warehouse.</p><p>It should be the first thing a Data Warehouse Architect does to define a Data Warehouse project.</p><h2>Free Data Warehouse Bus Matrix Excel Template</h2><p>Grab my free data warehouse bus matrix Excel template, which is shown in this post.</p><p class="button-wrapper" data-attrs="{&quot;url&quot;:&quot;https://dimodelo.substack.com/p/data-warehouse-bus-matrix-template&quot;,&quot;text&quot;:&quot;Free data warehouse matrix template ->&quot;,&quot;action&quot;:null,&quot;class&quot;:null}" data-component-name="ButtonCreateButton"><a class="button primary" href="/__u/dimodelo.substack.com/p/data-warehouse-bus-matrix-template"><span>Free data warehouse matrix template -&gt;</span></a></p><blockquote><p>&#8220;I&#8217;ve used this Bus Matrix spreadsheet on all my projects to help design, plan and estimate data warehouses and communicate the scope and progress to stakeholders.&#8221;</p></blockquote><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!rb0i!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4aceb814-d5e8-4668-b374-1c4a4d88f506_1082x770.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!rb0i!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4aceb814-d5e8-4668-b374-1c4a4d88f506_1082x770.png 424w, /__u/substackcdn.com/image/fetch/$s_!rb0i!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4aceb814-d5e8-4668-b374-1c4a4d88f506_1082x770.png 848w, /__u/substackcdn.com/image/fetch/$s_!rb0i!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4aceb814-d5e8-4668-b374-1c4a4d88f506_1082x770.png 1272w, /__u/substackcdn.com/image/fetch/$s_!rb0i!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4aceb814-d5e8-4668-b374-1c4a4d88f506_1082x770.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!rb0i!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4aceb814-d5e8-4668-b374-1c4a4d88f506_1082x770.png" width="1082" height="770" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/4aceb814-d5e8-4668-b374-1c4a4d88f506_1082x770.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:770,&quot;width&quot;:1082,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;Kimball Data Warehouse Bus Matrix Excel Template&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="Kimball Data Warehouse Bus Matrix Excel Template" title="Kimball Data Warehouse Bus Matrix Excel Template" srcset="/__u/substackcdn.com/image/fetch/$s_!rb0i!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4aceb814-d5e8-4668-b374-1c4a4d88f506_1082x770.png 424w, /__u/substackcdn.com/image/fetch/$s_!rb0i!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4aceb814-d5e8-4668-b374-1c4a4d88f506_1082x770.png 848w, /__u/substackcdn.com/image/fetch/$s_!rb0i!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4aceb814-d5e8-4668-b374-1c4a4d88f506_1082x770.png 1272w, /__u/substackcdn.com/image/fetch/$s_!rb0i!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4aceb814-d5e8-4668-b374-1c4a4d88f506_1082x770.png 1456w" sizes="100vw"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><h2>Why do you need a Data Warehouse Matrix?</h2><p>A Data Warehouse Matrix is a simple yet powerful communication tool. Its simplicity is its core strength, making it useful for communication that works at every level of the organization, from executives to end-users and developers.</p><p>A Data Warehouse matrix serves several purposes:</p><p>1.&nbsp;<strong>Capture Design</strong>: Succinctly capture the high-level design of the enterprise-wide data warehouse.</p><p>2.&nbsp;<strong>Communication</strong>: At a glance, communicate the scope, business process coverage and high-level design of the Data Warehouse to stakeholders, developers and end-users.</p><p>3.&nbsp;<strong>Estimate</strong>: With a few enhancements, Designers can use the Data Warehouse matrix to estimate the time required to build the Data Warehouse.</p><p>4.&nbsp;<strong>Plan</strong>: Assist in planning the delivery of each development iteration of the project whilst ensuring each iteration conforms to an overall design.</p><p>5.&nbsp;<strong>Progress</strong>: Communicate the progress of the project.</p><p><strong><a href="/__u/dimodelo.substack.com/p/data-warehouse-bus-matrix-template">Grab your free Data Warehouse Bus matrix template -&gt;</a></strong></p><h2>A Data Warehouse Bus Matrix example</h2><p>Below is an example of a very simple Data Warehouse Matrix.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!xIRW!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e26caa9-e35f-411e-92ee-a1081f302b6a_894x512.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!xIRW!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e26caa9-e35f-411e-92ee-a1081f302b6a_894x512.png 424w, /__u/substackcdn.com/image/fetch/$s_!xIRW!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e26caa9-e35f-411e-92ee-a1081f302b6a_894x512.png 848w, /__u/substackcdn.com/image/fetch/$s_!xIRW!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e26caa9-e35f-411e-92ee-a1081f302b6a_894x512.png 1272w, /__u/substackcdn.com/image/fetch/$s_!xIRW!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e26caa9-e35f-411e-92ee-a1081f302b6a_894x512.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!xIRW!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e26caa9-e35f-411e-92ee-a1081f302b6a_894x512.png" width="894" height="512" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/4e26caa9-e35f-411e-92ee-a1081f302b6a_894x512.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:512,&quot;width&quot;:894,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!xIRW!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e26caa9-e35f-411e-92ee-a1081f302b6a_894x512.png 424w, /__u/substackcdn.com/image/fetch/$s_!xIRW!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e26caa9-e35f-411e-92ee-a1081f302b6a_894x512.png 848w, /__u/substackcdn.com/image/fetch/$s_!xIRW!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e26caa9-e35f-411e-92ee-a1081f302b6a_894x512.png 1272w, /__u/substackcdn.com/image/fetch/$s_!xIRW!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F4e26caa9-e35f-411e-92ee-a1081f302b6a_894x512.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Example data warehouse matrix</figcaption></figure></div><p>On the rows of the Matrix are the Facts/Business Processes (e.g. Sales). On the columns are the Dimensions/Business Entities (e.g. Customer). The cells represent the relationships between the Facts and Dimensions. The number represents how many relationships exist between the Fact and Dimension. An empty cell means there is no relationship.</p><p>For example, the &#8220;Production&#8221; fact below is related to (or &#8220;dimensioned by&#8221;) the Dimensions Product, Staff and Calendar. This means an end-user can analyze &#8220;Production&#8221; measures by any combination of the Product, Staff, or Calendar Dimensions attributes.</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!H9aU!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6767a274-78a3-47b8-aae4-db97bc88d1f3_640x221.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!H9aU!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6767a274-78a3-47b8-aae4-db97bc88d1f3_640x221.png 424w, /__u/substackcdn.com/image/fetch/$s_!H9aU!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6767a274-78a3-47b8-aae4-db97bc88d1f3_640x221.png 848w, /__u/substackcdn.com/image/fetch/$s_!H9aU!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6767a274-78a3-47b8-aae4-db97bc88d1f3_640x221.png 1272w, /__u/substackcdn.com/image/fetch/$s_!H9aU!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6767a274-78a3-47b8-aae4-db97bc88d1f3_640x221.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!H9aU!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6767a274-78a3-47b8-aae4-db97bc88d1f3_640x221.png" width="640" height="221" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/6767a274-78a3-47b8-aae4-db97bc88d1f3_640x221.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:221,&quot;width&quot;:640,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!H9aU!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6767a274-78a3-47b8-aae4-db97bc88d1f3_640x221.png 424w, /__u/substackcdn.com/image/fetch/$s_!H9aU!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6767a274-78a3-47b8-aae4-db97bc88d1f3_640x221.png 848w, /__u/substackcdn.com/image/fetch/$s_!H9aU!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6767a274-78a3-47b8-aae4-db97bc88d1f3_640x221.png 1272w, /__u/substackcdn.com/image/fetch/$s_!H9aU!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F6767a274-78a3-47b8-aae4-db97bc88d1f3_640x221.png 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a><figcaption class="image-caption">Production fact</figcaption></figure></div><p>You will also notice that the Production fact shares the Product, Staff and Calendar dimensions with the Sales fact. When Facts share Dimensions, it&#8217;s known as &#8220;conformed&#8221; dimensions. That is, the facts &#8220;conform&#8221; to the same set of dimensions. The benefit of conformed dimensions is cross-business process analysis.</p><p>For example, the Product and Calendar dimensions shared between the Production and Sales facts mean we can analyze Sales vs Production for any given time period broken down by Product. If Facts share a Dimension, measures of those facts can be analyzed together on the same pivot table when slicing by that Dimension.</p><p>The Data Warehouse matrix is a very easy way to communicate the cross-business-process analysis capabilities of a data warehouse.</p><p>The matrix can also highlight issues with your design. For example, the matrix above shows the Sales Fact has no relationship with the Account Dimension. Users might have requested to see Sales broken down by Account and compare to current Accounts Receivables for that same Account. The Matrix shows this isn&#8217;t possible, and there is a need for an additional relationship between Sales and Account.</p><p><strong><a href="/__u/dimodelo.substack.com/p/data-warehouse-bus-matrix-template">Grab your free Data Warehouse Bus matrix template -&gt;</a></strong></p><h2>Data Warehouse Development Planning and Progress</h2><p>You can use the matrix to help&nbsp;<strong>plan your project</strong>. Generally, you won&#8217;t or can&#8217;t deliver the entire Data Warehouse at one time. Having a matrix allows you to deliver parts of the Data Warehouse while still maintaining an overall plan that integrates new Dimensions and Facts as they are created.</p><p>Initially, you will make decisions about which Facts are going to be the most valuable and deliver those first. But you will have to temper that decision based on complexity, which is partially determined by how many Dimensions a Fact table is related to.</p><p>While the project progresses, you can use colour to&nbsp;<strong>communicate project progress</strong>.</p><p>Continuing on from our previous example, the project has completed its first iteration and is currently working on the second. In the image below, the Bus matrix has been color-coded to communicate status.</p><ul><li><p>Green = done,</p></li><li><p>Yellow = in-progress</p></li><li><p>Blue = not started.</p></li></ul><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!WFxF!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5a942805-e3c0-401e-bda2-dd6615e4e93c_690x368.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!WFxF!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5a942805-e3c0-401e-bda2-dd6615e4e93c_690x368.png 424w, /__u/substackcdn.com/image/fetch/$s_!WFxF!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5a942805-e3c0-401e-bda2-dd6615e4e93c_690x368.png 848w, /__u/substackcdn.com/image/fetch/$s_!WFxF!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5a942805-e3c0-401e-bda2-dd6615e4e93c_690x368.png 1272w, /__u/substackcdn.com/image/fetch/$s_!WFxF!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5a942805-e3c0-401e-bda2-dd6615e4e93c_690x368.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!WFxF!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5a942805-e3c0-401e-bda2-dd6615e4e93c_690x368.png" width="690" height="368" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/5a942805-e3c0-401e-bda2-dd6615e4e93c_690x368.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:368,&quot;width&quot;:690,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!WFxF!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5a942805-e3c0-401e-bda2-dd6615e4e93c_690x368.png 424w, /__u/substackcdn.com/image/fetch/$s_!WFxF!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5a942805-e3c0-401e-bda2-dd6615e4e93c_690x368.png 848w, /__u/substackcdn.com/image/fetch/$s_!WFxF!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5a942805-e3c0-401e-bda2-dd6615e4e93c_690x368.png 1272w, /__u/substackcdn.com/image/fetch/$s_!WFxF!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5a942805-e3c0-401e-bda2-dd6615e4e93c_690x368.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a><figcaption class="image-caption">Data warehouse matrix status</figcaption></figure></div><p>In iteration one, the project delivered the Sales fact with some of its dimensions (shown in green). In the current iteration, the project is delivering the Production Fact with a single Product dimension (shown in yellow). Since we are delivering the Product dimension, we are also augmenting the Sales fact with the Product dimension. In this case, the Production fact was considered a quick win since the majority of its Dimensions were already delivered.</p><p>Using colour-coding is a simple but effective way of quickly communicating overall progress.</p><p><strong><a href="/__u/dimodelo.substack.com/p/data-warehouse-bus-matrix-template">Grab your free Data Warehouse Bus matrix template -&gt;</a></strong></p><h2>What does a Data Warehouse Matrix communicate?</h2><p>Depending on the audience, a Data Warehouse matrix can communicate different things. The audience can be broken down into:</p><ul><li><p>Executives/Project Management</p></li><li><p>End Users/Business Analysts</p></li><li><p>Developers</p></li></ul><h4>Executives/Project Management:</h4><ul><li><p>The <strong>scope </strong>of the data warehouse.</p></li><li><p>The <strong>coverage </strong>across the value chain and business processes.</p></li><li><p>The <strong>effort </strong>required to complete the Data Warehouse. A Data Warehouse Matrix enhanced with automated estimating can communicate effort to Project Managers for duration and cost Estimation.</p></li><li><p>Tracking and communicating <strong>progress </strong>is possible by adding colour coding to the Data Warehouse matrix.</p></li></ul><h4>End Users/Business Analysts:</h4><ul><li><p>How end-user analytics requirements are satisfied by the Data Warehouse.</p></li><li><p>How end-user requirements fit within a broader enterprise-wide reporting framework.</p></li><li><p>How end-users can analyze a given Fact by a given set of Dimension attributes.</p></li><li><p>How conformed dimensions enable integrated reporting across business processes.</p></li></ul><h4>Developers:</h4><ul><li><p>A master plan for data warehouse delivery, providing context for current iterations.</p></li><li><p>Overall high-level design.</p></li><li><p>Progress. Tracking and communicating progress is possible by adding colour coding to the Data Warehouse matrix.</p></li></ul><p class="button-wrapper" data-attrs="{&quot;url&quot;:&quot;https://dimodelo.substack.com/p/data-warehouse-bus-matrix-template&quot;,&quot;text&quot;:&quot;Free Data Warehouse Matrix Template&quot;,&quot;action&quot;:null,&quot;class&quot;:null}" data-component-name="ButtonCreateButton"><a class="button primary" href="/__u/dimodelo.substack.com/p/data-warehouse-bus-matrix-template"><span>Free Data Warehouse Matrix Template</span></a></p><p></p>]]></content:encoded></item><item><title><![CDATA[What is a Semantic Layer? (and why you need one)]]></title><description><![CDATA[What is a Semantic Layer]]></description><link>https://dimodelo.substack.com/p/what-is-a-semantic-layer-what-why-how-and-more</link><guid isPermaLink="false">https://dimodelo.substack.com/p/what-is-a-semantic-layer-what-why-how-and-more</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Tue, 17 Oct 2023 06:22:06 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/eb017302-4dbc-4937-a864-30a5879e689c_714x335.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<h2>What is a Semantic Layer</h2><p>A semantic layer exists to present data to users as a set of related and commonly understood business entities, terms and metrics.</p><p>A semantic layer is typically the &#8220;top&#8221; layer of a <a href="/__u/dimodelo.substack.com/p/what-is-a-data-warehouse-and-why-you-need-one/">data warehouse</a>/lakehouse. It is accessible to end users and report developers, who use it as the source for reports, dashboards, and ad hoc analysis.</p><p>A semantic layer is important because it fosters a shared understanding of information across the business. It supports the autonomous development of consistent reports, analysis and dashboards by end users.</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!Kb5j!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F47b94cb1-5b88-4c73-9da0-78c4fd2d6d62_400x236.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!Kb5j!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F47b94cb1-5b88-4c73-9da0-78c4fd2d6d62_400x236.png 424w, /__u/substackcdn.com/image/fetch/$s_!Kb5j!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F47b94cb1-5b88-4c73-9da0-78c4fd2d6d62_400x236.png 848w, /__u/substackcdn.com/image/fetch/$s_!Kb5j!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F47b94cb1-5b88-4c73-9da0-78c4fd2d6d62_400x236.png 1272w, /__u/substackcdn.com/image/fetch/$s_!Kb5j!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F47b94cb1-5b88-4c73-9da0-78c4fd2d6d62_400x236.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!Kb5j!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F47b94cb1-5b88-4c73-9da0-78c4fd2d6d62_400x236.png" width="400" height="236" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/47b94cb1-5b88-4c73-9da0-78c4fd2d6d62_400x236.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:236,&quot;width&quot;:400,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;A semantic layer is typically modelled with a star schema&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="A semantic layer is typically modelled with a star schema" title="A semantic layer is typically modelled with a star schema" srcset="/__u/substackcdn.com/image/fetch/$s_!Kb5j!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F47b94cb1-5b88-4c73-9da0-78c4fd2d6d62_400x236.png 424w, /__u/substackcdn.com/image/fetch/$s_!Kb5j!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F47b94cb1-5b88-4c73-9da0-78c4fd2d6d62_400x236.png 848w, /__u/substackcdn.com/image/fetch/$s_!Kb5j!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F47b94cb1-5b88-4c73-9da0-78c4fd2d6d62_400x236.png 1272w, /__u/substackcdn.com/image/fetch/$s_!Kb5j!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F47b94cb1-5b88-4c73-9da0-78c4fd2d6d62_400x236.png 1456w" sizes="100vw" fetchpriority="high"></picture><div></div></div></a></figure></div><p>A semantic layer is:</p><ol><li><p><strong>First, a business glossary</strong>. The basis of a semantic layer is a glossary of related commonly understood business entities, terms and metrics, e.g., The concepts of a Customer, Product, Sale and the relationship between Sales and Products, and Sales and Customers.</p></li><li><p><strong>Represented as a &#8220;business view&#8221; of data</strong>. Physically, the &#8220;business glossary&#8221; exists as a &#8220;business view&#8221; of enterprise data. The &#8220;business view&#8221; is implemented in the semantic layer. The semantic layer is typically the highest/final layer of a <a href="/__u/dimodelo.substack.com/p/what-is-a-data-warehouse/">data warehouse</a> or data lakehouse implementation. The raw enterprise data undergoes a series of transformations to arrive at the semantic layer&#8217;s &#8220;business view&#8221; format. The most common &#8220;business view&#8221; format is a <a href="/__u/dimodelo.substack.com/p/what-is-dimensional-modeling-introduction/">dimensional model</a>.</p></li><li><p><strong>Accessible to BI developers and end users</strong>. The semantic layer is accessible to end users, data analysts and BI developers. It&#8217;s the source of data for reports, ad-hoc analysis and dashboards.</p></li><li><p><strong>Supports Autonomy</strong>. A semantic layer supports autonomous access and navigation of the data. It supports self-service BI and ad-hoc (drag-drop) analysis.</p></li><li><p><strong>Fosters a shared understanding</strong>. A semantic layer fosters a common understanding of enterprise data amongst all business users.</p></li></ol><h2>Why do you need a Semantic Layer?</h2><p>In large and small businesses today, there are challenges in producing consistent reports.</p><p>Without a semantic layer, users, data analysts and BI developers inevitably use data from a variety of sources to develop reports, etc. These reports will often contain conflicting definitions and calculations. These contradictory reports generate a lot of confusion. Business users waste time arguing about these differences with little possibility of resolution. Ultimately, without a semantic layer, the quality and trust in the data on which decisions are made is eroded.</p><p>In contrast, semantic layers provide a shared understanding of business terminology and a &#8220;single source of truth&#8221; for reporting etc. Users, data analysts and BI developers use this &#8220;single source of truth&#8221; as the source of all reports, etc. This promotes a common business language and understanding and fosters trust, quality, and user collaboration. In addition, it encourages reuse and reduces duplication of effort and waste.</p><p>Physically, semantic software in a Data Warehouse or Data Lakehouse architecture provides the following benefits:</p><ol><li><p><strong>High-performance aggregated queries</strong>. Sub-second response time to aggregated queries over billions of rows.</p></li><li><p><strong>Augments and Enhanced Information</strong>. The ability to enhance and simplify the information in the underlying Data Warehouse or Data Lakehouse, including:</p><ul><li><p>&#8220;Cleaning up the model&#8221; to Hide tables, columns, and relationships irrelevant to the business.</p></li><li><p>Adding Hierarchies. Hierarchies enable hierarchical reports, drill-downs and more straightforward navigation.</p></li><li><p>Adding reusable context-aware calculated metrics.</p></li><li><p>Renaming tables and columns if necessary (although your data warehouse, if modelled correctly, should already use the correct naming standard).</p></li></ul></li><li><p><strong>Unified Data</strong>. Semantic models can combine data from multiple sources. Indeed, an end user could enhance the data warehouse with their own data source in the semantic layer.</p></li><li><p><strong>Support for BI tools</strong>. Many BI tools natively support connecting to and querying semantic layer software.</p></li><li><p><strong>Context-Aware Security</strong>. Restrict data access based on tables, rows, columns and formulas.</p></li></ol><h2>The different Types of Semantic Layers</h2><p>The semantic layer tends to fall into four categories:</p><h4>1. <strong>Data Store or fat semantic layer</strong></h4><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!Ei3z!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbe3991b8-7fee-42f5-a03d-a7235a89b025_714x335.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!Ei3z!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbe3991b8-7fee-42f5-a03d-a7235a89b025_714x335.png 424w, /__u/substackcdn.com/image/fetch/$s_!Ei3z!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbe3991b8-7fee-42f5-a03d-a7235a89b025_714x335.png 848w, /__u/substackcdn.com/image/fetch/$s_!Ei3z!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbe3991b8-7fee-42f5-a03d-a7235a89b025_714x335.png 1272w, /__u/substackcdn.com/image/fetch/$s_!Ei3z!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbe3991b8-7fee-42f5-a03d-a7235a89b025_714x335.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!Ei3z!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbe3991b8-7fee-42f5-a03d-a7235a89b025_714x335.png" width="714" height="335" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/be3991b8-7fee-42f5-a03d-a7235a89b025_714x335.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:335,&quot;width&quot;:714,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;fat datastore type semantic layer&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="fat datastore type semantic layer" title="fat datastore type semantic layer" srcset="/__u/substackcdn.com/image/fetch/$s_!Ei3z!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbe3991b8-7fee-42f5-a03d-a7235a89b025_714x335.png 424w, /__u/substackcdn.com/image/fetch/$s_!Ei3z!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbe3991b8-7fee-42f5-a03d-a7235a89b025_714x335.png 848w, /__u/substackcdn.com/image/fetch/$s_!Ei3z!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbe3991b8-7fee-42f5-a03d-a7235a89b025_714x335.png 1272w, /__u/substackcdn.com/image/fetch/$s_!Ei3z!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbe3991b8-7fee-42f5-a03d-a7235a89b025_714x335.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>The Datastore flavour contains a complete additional copy of the Data. The data is stored in a proprietary, highly compressed and optimised format (usually column store). This flavour comes with an internally optimised vector-based query engine. <strong>The Datastore flavour tends to perform better than the Virtual flavour</strong> because these data stores are structured to support high-performance aggregated queries. The emphasis is on aggregated. The data store is usually transient and re-loaded periodically from the Data Warehouse. Example technologies include Microsoft Azure Analysis Services, PowerBI data sets, Kyligence, GoodData, <a href="https://druid.apache.org/">Apache Druid</a> and Apache Pinot.</p><ul><li><p><strong>Advantages</strong>:</p><ul><li><p>High performance for aggregated queries</p></li><li><p>Easier to define security.</p></li><li><p>It contains functional query languages that make it possible to define complex metrics.</p></li></ul></li><li><p><strong>Disadvantages</strong>:</p><ul><li><p>Increased complexity and cost to load an additional datastore.</p></li></ul></li></ul><h4>2. <strong>Virtual or thin semantic layer</strong></h4><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!PaxZ!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5b9ea1a9-de32-402a-8ca1-67f23a301b74_712x268.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!PaxZ!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5b9ea1a9-de32-402a-8ca1-67f23a301b74_712x268.png 424w, /__u/substackcdn.com/image/fetch/$s_!PaxZ!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5b9ea1a9-de32-402a-8ca1-67f23a301b74_712x268.png 848w, /__u/substackcdn.com/image/fetch/$s_!PaxZ!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5b9ea1a9-de32-402a-8ca1-67f23a301b74_712x268.png 1272w, /__u/substackcdn.com/image/fetch/$s_!PaxZ!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5b9ea1a9-de32-402a-8ca1-67f23a301b74_712x268.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!PaxZ!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5b9ea1a9-de32-402a-8ca1-67f23a301b74_712x268.png" width="712" height="268" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/5b9ea1a9-de32-402a-8ca1-67f23a301b74_712x268.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:268,&quot;width&quot;:712,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;thin virtual semantic layer&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="thin virtual semantic layer" title="thin virtual semantic layer" srcset="/__u/substackcdn.com/image/fetch/$s_!PaxZ!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5b9ea1a9-de32-402a-8ca1-67f23a301b74_712x268.png 424w, /__u/substackcdn.com/image/fetch/$s_!PaxZ!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5b9ea1a9-de32-402a-8ca1-67f23a301b74_712x268.png 848w, /__u/substackcdn.com/image/fetch/$s_!PaxZ!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5b9ea1a9-de32-402a-8ca1-67f23a301b74_712x268.png 1272w, /__u/substackcdn.com/image/fetch/$s_!PaxZ!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5b9ea1a9-de32-402a-8ca1-67f23a301b74_712x268.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>The virtual semantic layer doesn&#8217;t store a separate copy of the data (although it might cache data for performance). Instead, the virtual semantic layer contains the logic that defines the semantic model. When a query is executed, <strong>the virtual semantic layer acts as a proxy and generates and runs an SQL query against the underlying data source(s)</strong>. Examples of technologies include Cube, Malloy, LookML, Metriql, AtScale, MetricFlow, Metlo, and Denodo.</p><ul><li><p><strong>Advantages</strong>:</p><ul><li><p>Avoids data movement to an additional data store.Lower complexity.Lower cost due to less data storage.</p></li></ul></li><li><p><strong>Disadvantages</strong>:</p><ul><li><p>Tend to be slower than data store-based semantic layers optimised for aggregated queries. Caching and pre-computation can elevate some of this disparity, but not all; frankly, it moves this solution toward the hybrid option anyway.</p></li></ul></li></ul><h4>3. <strong>Hybrid semantic layer</strong></h4><p>Hybrid flavours support both datastore and virtual modes. Developers can generally define which tables within a semantic model are stored vs virtual. This can help with the trade-offs of performance vs complexity/capacity. In some cases, the data may be so large it is beyond the capacity of the semantic platform to store it. It could be argued that virtual caching is one way to achieve a hybrid model. A better example is Power BI datasets that allow a single semantic model to have a mix of stored vs virtual (direct query) tables.</p><h4>4. <strong>Meta Semantic layer</strong></h4><p>This is a relatively new development in semantic modelling. Effectively, companies like dbt allow developers to define metrics in a platform-agnostic language. The idea is that dbt can generate the code for a given metric for any supported platform. That&#8217;s the idea, at least. Think potentially generating a Power BI dataset or another language for a different platform. This provides portability. It&#8217;s very early days, and so far, dbt&#8217;s implementation is more focused on supporting its own dbt cloud semantic server. However, the original open-source and open-platform idea persists. Time will tell. <a href="https://docs.getdbt.com/docs/use-dbt-semantic-layer/dbt-sl">dbt Semantic Layer | dbt Developer Hub (getdbt.com)</a></p><h2>How are semantic layers implemented?</h2><p>From a physical point of view, a semantic layer is implemented using specialized software. There are several flavours, which we will expand on in this section.</p><h3>1. Semantic layer implemented within a BI tool</h3><p>Modern BI reporting and analysis tools like Power BI, Tableau and Qlik allow data analysts to model a semantic layer directly within a dashboard or report. Some tools will enable you to deploy the semantic model independently from a report and have it act as the semantic layer that many dashboards and reports share.</p><p>Ultimately, this approach has issues. An undisciplined proliferation of separate semantic models within dashboards and reports defeats the purpose of a shared semantic layer. What is needed is a disciplined development approach that enforces shared data models.</p><p>Power BI has the most comprehensive use case as a semantic layer among the most popular BI tools. While it can support a semantic layer coupled with a report, it can also support a scenario as a stand-alone semantic layer. First, a data set can be published independently from a report and shared by many reports. Power BI premium capacity supports large data sets beyond the typical 10GB up to the capacity size. Power BI has an XMLA endpoint and a REST API that allows external applications to make queries. It enables users to create composite models to supplement data, e.g., a budget Excel spreadsheet combined with actuals from a data warehouse. Power BI supports stored, virtual and hybrid query models. People have even <a href="https://visualbi.com/blogs/tableau/connect-tableau-to-power-bi-datasets/">used Power BI as the semantic layer and Tableau as the client</a> via XLMA endpoints. It also has a highly capable functional language, DAX, an internal Vertipaq/tabular data store, and a query engine.</p><p>In contrast, Tableau&#8217;s strength is its visual aesthetics. It does support some semantic modelling concepts in its data model. It also supports high-performance queries with its Hyper query engine. However, it lacks the concept of publishing a data model as a stand-alone semantic layer. It also lacks the rich analytics language like DAX.</p><h3>Semantic Layer implemented in a Data Warehouse/Data Lakehouse Architecture</h3><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!lwOA!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3d48a3d4-d171-47e5-bb9e-371847b523c9_418x610.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!lwOA!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3d48a3d4-d171-47e5-bb9e-371847b523c9_418x610.png 424w, /__u/substackcdn.com/image/fetch/$s_!lwOA!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3d48a3d4-d171-47e5-bb9e-371847b523c9_418x610.png 848w, /__u/substackcdn.com/image/fetch/$s_!lwOA!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3d48a3d4-d171-47e5-bb9e-371847b523c9_418x610.png 1272w, /__u/substackcdn.com/image/fetch/$s_!lwOA!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3d48a3d4-d171-47e5-bb9e-371847b523c9_418x610.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!lwOA!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3d48a3d4-d171-47e5-bb9e-371847b523c9_418x610.png" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/3d48a3d4-d171-47e5-bb9e-371847b523c9_418x610.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:null,&quot;width&quot;:null,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;data warehouse/data lake architecture&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="data warehouse/data lake architecture" title="data warehouse/data lake architecture" srcset="/__u/substackcdn.com/image/fetch/$s_!lwOA!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3d48a3d4-d171-47e5-bb9e-371847b523c9_418x610.png 424w, /__u/substackcdn.com/image/fetch/$s_!lwOA!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3d48a3d4-d171-47e5-bb9e-371847b523c9_418x610.png 848w, /__u/substackcdn.com/image/fetch/$s_!lwOA!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3d48a3d4-d171-47e5-bb9e-371847b523c9_418x610.png 1272w, /__u/substackcdn.com/image/fetch/$s_!lwOA!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F3d48a3d4-d171-47e5-bb9e-371847b523c9_418x610.png 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a></figure></div><p>The semantic layer is the final layer of a data warehouse/data lakehouse architecture.</p><p>The semantic layer sits between the presentation layer (the gold layer in Data Lakehouse) and the reports/analysis/dashboards. End users can view, navigate, and query the semantic model through a BI tool.</p><p>The best practice is to model the presentation/gold layer as a dimensional model. A dimensional model <a href="/__u/dimodelo.substack.com/p/the-star-schema/">star schema</a> lends itself nicely to semantic layer entities. The core of a dimensional model is business processes, which are modelled as facts with their measures/metrics. The business entities involved in business processes are modelled as <a href="/__u/dimodelo.substack.com/p/dimension-concepts/">dimensions</a> with their descriptive attributes.</p><p>Most semantic modelling work and transformation occurs in the presentation/gold layers. The semantic layer should map directly to the Facts and Dimensions in that layer.</p><p>So, if the semantic layer looks like the presentation layer, why need a separate semantic layer?</p><p>As discussed before, the semantic layer software offers:</p><ol><li><p><strong>High-performance aggregated queries</strong>.</p></li><li><p><strong>Augments and Enhanced Information</strong>. Enhances and simplifies the information in the underlying Data Warehouse or Data Lakehouse. This includes:</p><ul><li><p>Hiding tables, columns, and relationships irrelevant to the business, including surrogate keys and management columns.</p></li><li><p>Adding Hierarchies. Hierarchies enable hierarchical reports, drill-downs and more straightforward navigation. Adding reusable context-aware calculated metrics.</p></li></ul><ul><li><p>Renaming tables and columns if necessary (although your data warehouse, if modelled correctly, should already use the correct naming standard).</p></li></ul></li><li><p><strong>Unified Data</strong>. Semantic models can combine data from multiple sources. Indeed, an end user could enhance the data warehouse with their own data source at the semantic layer.</p></li><li><p><strong>Supports BI tools</strong>. Many BI tools natively support connecting to and querying semantic layer software.</p></li><li><p><strong>Context-Aware Security</strong>. Restrict data access based on tables, rows, columns and formulas.</p></li><li><p><strong>Supports ad hoc analysis</strong>. Provides an interface that BI tools use to enable ad-hoc, drag-and-drop, pivotable style data analysis. The data store and query engine behind semantic layer software makes this possible.</p></li></ol><h3>Universal Semantic Layer</h3><p>A universal semantic layer is more about a philosophy or methodology. Personally, I advocate for always building a semantic layer on top of a data warehouse/data lakehouse, and, therefore, don&#8217;t endorse the &#8220;Universal Semantic Layer&#8221; concept.</p><p>&#8220;Universal Semantic Layer&#8221; advocates believe building a data warehouse requires too much effort. They advocate skipping the data warehouse build. Instead, you connect your semantic layer directly to source systems or a raw dataset in a common data store. Then, the semantic layer is used to join and transform that data into the semantic model. When a user accesses the semantic layer, the semantic layer software generates and orchestrates the queries across many sources and joins the disparate result sets to produce the final result.</p><p>This approach often lends itself to the &#8220;virtual&#8221; type of semantic layer software, where the semantic layer is just a thin veneer with a semantic model.</p><p>An obvious issue with this approach is performance. The underlying data sources are not specialised in aggregated queries. Joining across source systems often leads to inefficient query plans. The queries can take minutes or hours to return results. To counter this issue, vendors introduce pre-processing and caching, but frankly, this can only achieve so much. Some have even taken to embedding an analytics database behind the virtual semantic model, shifting source data to this analytics database. This sounds a lot like a data warehouse&#8230; just worse.</p><p>Rather than saving the developer&#8217;s effort, it simply shifts it from the data warehouse/data lakehouse (where it belongs) to the semantic layer. The semantic layer is not well suited to implementing transformations. It also shifts the processing workload from batch/overnight data warehouse loads, where the data is transformed and prepared by the data warehouse/data lakehouse for the semantic layer, to query time, when the end user has to wait for the transformation to occur while they run their report.</p><p>The semantic layer becomes the sole purveyor of the semantic model. The modern data warehouse is designed to support various usage scenarios besides ad-hoc analysis, reports and BI. Today, the modern data warehouse must support Data Science workloads, non-real-time data integration (i.e. reverse ETL), &nbsp;near-real-time analytics, etc. &nbsp;These workloads often require fine-grained and/or high-volume data rather than aggregated data. Semantic layer software excels at aggregated queries but not fine-grained high-volume row-based ones. If you have a Data Warehouse/Data Lakehouse, use it to serve these fine-grained, high-volume, row-based queries. Then, use your semantic layer for what it is best for &#8211; serving aggregated analytical queries. Horses for courses!</p><h2>The History and Future of Semantic Layers</h2><p>Prepare for a rant!</p><p>Unfortunately, the concept of a semantic layer got lost in the vendor-driven, VC-backed &#8220;data warehouse is dead&#8221;, data analyst-centric collective nightmare of the modern data stack that valued agility over all else! In the melee, we lost the consistency of meaning, reuse and sustainable data assets that data warehouses were designed to deliver.</p><p><strong>The problem with data warehouses was never the concept; it was the execution</strong>. Back in the &#8217;90s and &#8217;00s, business users were very frustrated by how long it took to create what seemed like a fairly simple report. Couple that with the explosion of data that stressed the state-of-the-art databases at the time, and it&#8217;s true that something had to change.</p><p>Personally, I believe we should have (and could have &#8211; with automation) addressed the methodology of delivering data warehouses. Unfortunately, the data warehouse baby got thrown out with the bath water. Instead, we got &#8220;Big Data&#8221; (Remember Hadoop, etc.) and Self-Service BI. The &#8220;Big Data&#8221; hype cycle was driven by the very largest organisations (the Facebooks and Googles of the world) and pumped by the consultancy industry onto organisations that didn&#8217;t have the same big data issues. Consultancies love this kind of disruption. It puts bums on seats and $ in the bank. &#8220;Big Data&#8221; was a monumental flop, but out of the ashes emerged HDFS and Spark. Spark is the open-source distributed computing technology underpinning Databricks, Microsoft Fabric and other analytics platforms. Self-service BI was a myth that gave organisations the excuse to favour agility over sustainability. The result was &#8220;data swamps&#8221; and a reemergence of the &#8220;single version of the truth&#8221; problem and other issues that data warehouses were designed to fix.</p><p>However, now, finally, things are changing. <strong>We are seeing the signs of the industry awakening from its coma</strong>. The emergence of the Data Lakehouse architecture acknowledges that the Data Warehouse concept is still valid. The Modern data warehouse, I think, is still overly complicated, but now, rather than being purely reporting/dashboard/analysis focussed, we have a unified platform that can serve more usage scenarios like Data science/analysis, real-time analytics and ETL, operational system analytics APIs, embedded BI and reverse ETL.</p><p>Even better news: <strong>the industry is recovering from its amnesia around semantic layers</strong>. In the 90s and 00s, semantic layers were regularly implemented with software like Microsoft Analysis Services, Business Objects Universe, etc. Unfortunately, semantic layers didn&#8217;t fit the narrative and were discounted and &#8220;forgotten&#8221;. Thankfully, the semantic layer is making a renaissance, as it should, as businesses encounter the reemergence of the problems that data warehouses were designed to solve.</p><p>There is new (and existing) software that is focused on implementing a Semantic layer. The emerging software sometimes uses new terms (e.g. Headless BI, Metrics Layer) as synonyms for a symantic layer. Headless BI may be slightly different as it implies that the semantic layer is not delivered within or alongside a visualisation platform.</p><p>The software can be divided into roughly 3 groups:</p><ol><li><p>Stand-alone tools like Cube, AtScale, Denodo, Kyligence.</p></li><li><p>Embedded within a Visualization platform. E.g. <a href="https://www.gooddata.com/developers/cloud-native/doc/cloud/introduction/">GoodData</a>, PowerBI, <a href="https://cloud.google.com/looker/docs/what-is-lookml#:~:text=LookML%20stands%20for%20Looker%20Modeling,relationships%20in%20your%20SQL%20database.">LookML</a>.</p></li><li><p>Meta or Virtual layers like the dbt offering. In dbt Core/Cloud, it&#8217;s possible to define metrics over your models using a metrics language. Dbt is developing a dbt Server in dbt Cloud that allows a visualisation client to connect in real-time, get metadata about available metrics, and then query the dbt server. The dbt server interprets the query using the metric definitions, generates an SQL query, executes against the underlying database, and returns the result. Other similar tools work in a similar way but have other strengths. Examples are <a href="https://www.youtube.com/watch?v=VQ0UFGSHV9o">Malloy</a>, <a href="https://metriql.com/faq/">Metriql</a>, <a href="https://github.com/dbt-labs/metricflow">MetricFlow</a>, and <a href="https://www.lightdash.com/#features">Lightdash</a>.</p></li></ol><p>Semantic later software has needed to evolve from the narrow BI focus of the 90s and 00&#8217;s to serve a more diverse set of usage scenarios of the modern data warehouse. A semantic layer must now be accessible for more usage scenarios like Data science/analytics, operational embedded BI, reverse ETL, etc.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!jkII!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbadd44b2-cbfa-4790-ba19-952943e63335_340x314.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!jkII!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbadd44b2-cbfa-4790-ba19-952943e63335_340x314.png 424w, /__u/substackcdn.com/image/fetch/$s_!jkII!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbadd44b2-cbfa-4790-ba19-952943e63335_340x314.png 848w, /__u/substackcdn.com/image/fetch/$s_!jkII!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbadd44b2-cbfa-4790-ba19-952943e63335_340x314.png 1272w, /__u/substackcdn.com/image/fetch/$s_!jkII!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbadd44b2-cbfa-4790-ba19-952943e63335_340x314.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!jkII!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbadd44b2-cbfa-4790-ba19-952943e63335_340x314.png" width="340" height="314" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/badd44b2-cbfa-4790-ba19-952943e63335_340x314.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:314,&quot;width&quot;:340,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;future semantic layer&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="future semantic layer" title="future semantic layer" srcset="/__u/substackcdn.com/image/fetch/$s_!jkII!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbadd44b2-cbfa-4790-ba19-952943e63335_340x314.png 424w, /__u/substackcdn.com/image/fetch/$s_!jkII!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbadd44b2-cbfa-4790-ba19-952943e63335_340x314.png 848w, /__u/substackcdn.com/image/fetch/$s_!jkII!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbadd44b2-cbfa-4790-ba19-952943e63335_340x314.png 1272w, /__u/substackcdn.com/image/fetch/$s_!jkII!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fbadd44b2-cbfa-4790-ba19-952943e63335_340x314.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>Thankfully, nearly all of the above tools have responded to this need. Many provide APIs, SDKs for Python, JDBC/ODBC interfaces, Robust metrics language, etc. Semantic layers are now able to play a wider role in promoting a common business language for end users and data professionals across any usage scenario.</p><p>The future for semantic layers is looking bright!</p>]]></content:encoded></item><item><title><![CDATA[Understanding Extract Transform and Load Design]]></title><description><![CDATA[ETL stands for Extract, Transform and Load. It refers to the process of extracting data from the Source systems, transforming it into the star schema format and loading it into a relational Data Warho]]></description><link>https://dimodelo.substack.com/p/understanding-extract-transform-and-load-design</link><guid isPermaLink="false">https://dimodelo.substack.com/p/understanding-extract-transform-and-load-design</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Sun, 31 Jan 2021 07:45:00 GMT</pubDate><enclosure url="https://substackcdn.com/image/fetch/$s_!PlCA!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F11d53975-3aca-4bdc-b987-b4b141fd63d3_1137x386.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<h1><strong>Understanding Extract Transform and Load Design</strong></h1><p>ETL stands for Extract, Transform and Load. It refers to the process of extracting data from the Source systems, transforming it into the star schema format and loading it into the relational Data Warehouse. Development of an ETL process is the major cost in delivering a Business Intelligence Solution. Up to 80% of your cost will be in developing the ETL.</p><p>ETL is complex. You could write an entire book about ETL, and several people have including <a href="https://www.kimballgroup.com/data-warehouse-business-intelligence-resources/books/data-warehouse-dw-etl-toolkit/">Kimball</a> himself, including the <a href="https://www.kimballgroup.com/data-warehouse-business-intelligence-resources/kimball-techniques/etl-architecture-34-subsystems/">34 Subsystems of ETL</a>. This section will just provide an overview of ETL processes. </p><p>On the surface ETL looks simple. It&#8217;s merely extracting data from one data source and inserting it into another. But once you delve in to it, it becomes more difficult with lots of use cases that must be managed. For example, how do you handle the following:</p><ul><li><p>Inserted, Update, Deleted at Source.</p></li><li><p>Late arriving Rows.</p></li><li><p>Duplicates.</p></li><li><p>Persisting data and keeping an accurate history.</p></li><li><p>Heterogeneous Source systems and Connectivity.</p></li><li><p>Identifying changed data at source.</p></li><li><p>Identifying changed data at target.</p></li><li><p>Deleted Rows being reinstated.</p></li><li><p>Type 1 and 2 SCD. Type 1 Only, Type 2 Only and Type 1 and 2 mixed Dimensions.</p></li><li><p>Schema changes of Source and Target entities.</p></li><li><p>Data Quality.</p></li><li><p>Full,Partial or Incremental sources and joins across each source.</p></li><li><p>Restarting failed processes.</p></li><li><p>Deployment to Multiple Environments.</p></li><li><p>Scheduling and Orchestrating Batches.</p></li></ul><p>And that&#8217;s just the start. It can take several months at least to derive effective ETL patterns.</p><p>In addition, ETL techniques are constantly changing. With the advent of the cloud, with a limited &#8220;pipe&#8221; between on-premise data sources and a cloud based data warehouse, and with different data load techniques targeting new technologies (Massive Parallel Processing Databases, Data Lakes, Big Data), the nature of ETL has changed significantly. ETL that worked on on-premise databases, won&#8217;t work for the cloud environment.</p><h2><strong>ETL vs ELT</strong></h2><p>Extract Transform/load (ETL) is an integration approach that pulls information from remote sources, transforms it into defined formats and styles, then loads it into databases, data sources, or data warehouses.</p><p>Extract/load/transform (ELT) similarly extracts data from one or multiple remote sources, but then loads it into the target data warehouse without any other formatting. The transformation of data, in an ELT process, happens within the target database. ELT asks less of remote sources, requiring only their raw and unprepared data.</p><p>ELT is gaining popularity because of the exponential growth of high scale processing power with database platforms themselves, like MPP databases, Big Data Clusters etc. ELT also has the advantage of keeping large amounts of historical unprocessed data on hand ready for the day it may be needed for new analysis.</p><h2><strong>ETL Process</strong></h2><p>There are as many ways to design ETL as their are designers. The diagram below describes the ETL and Data stores utilized by Dimodelo Data Warehouse Studio when generating a Data Warehouse solution. This borrows heavily from the Kimball methodology, but also incorporates our learning over many data warehouse implementations, the advent of the persistent staging concept, and the advent of Cloud based Data Warehouse solutions.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="/__u/substackcdn.com/image/fetch/$s_!PlCA!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F11d53975-3aca-4bdc-b987-b4b141fd63d3_1137x386.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="/__u/substackcdn.com/image/fetch/$s_!PlCA!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F11d53975-3aca-4bdc-b987-b4b141fd63d3_1137x386.png 424w, /__u/substackcdn.com/image/fetch/$s_!PlCA!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F11d53975-3aca-4bdc-b987-b4b141fd63d3_1137x386.png 848w, /__u/substackcdn.com/image/fetch/$s_!PlCA!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F11d53975-3aca-4bdc-b987-b4b141fd63d3_1137x386.png 1272w, /__u/substackcdn.com/image/fetch/$s_!PlCA!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_webp, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F11d53975-3aca-4bdc-b987-b4b141fd63d3_1137x386.png 1456w" sizes="100vw"><img src="/__u/substackcdn.com/image/fetch/$s_!PlCA!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F11d53975-3aca-4bdc-b987-b4b141fd63d3_1137x386.png" width="1137" height="386" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/11d53975-3aca-4bdc-b987-b4b141fd63d3_1137x386.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:386,&quot;width&quot;:1137,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:&quot;&quot;,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" title="" srcset="/__u/substackcdn.com/image/fetch/$s_!PlCA!, /__u/dimodelo.substack.com/w_424, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F11d53975-3aca-4bdc-b987-b4b141fd63d3_1137x386.png 424w, /__u/substackcdn.com/image/fetch/$s_!PlCA!, /__u/dimodelo.substack.com/w_848, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F11d53975-3aca-4bdc-b987-b4b141fd63d3_1137x386.png 848w, /__u/substackcdn.com/image/fetch/$s_!PlCA!, /__u/dimodelo.substack.com/w_1272, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F11d53975-3aca-4bdc-b987-b4b141fd63d3_1137x386.png 1272w, /__u/substackcdn.com/image/fetch/$s_!PlCA!, /__u/dimodelo.substack.com/w_1456, /__u/dimodelo.substack.com/c_limit, /__u/dimodelo.substack.com/f_auto, /__u/dimodelo.substack.com/q_auto:good, /__u/dimodelo.substack.com/fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F11d53975-3aca-4bdc-b987-b4b141fd63d3_1137x386.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><h3><strong>Extract</strong></h3><p>The extract process pulls data from a source system, usually on a nightly basis. Source systems can include Databases, Text Files, Excel spread sheets, or any other kind of source data. The data is written to a <strong>Landing data store</strong>, typically a local or cloud based file system ready for loading into the Staging/Persistent Layer. Conceptually, because of it&#8217;s file based nature, the Landing data store could be the raw data layer of a Data Lake. For the purposes of the Data Warehouse, the Landing Data Store is transient, meaning it doesn&#8217;t persist the data between ETL batch runs. Several patterns for Extract can be employed:</p><ul><li><p><strong>Full Extract</strong>. All the data in the source entity is extracted. In this case change data detection occurs during Load.</p></li><li><p><strong>Incremental Extract</strong>. Only the changed data is extracted from the source. In this case, the Load does not need to do change detection. This method is much faster. However, the source entity must support it. For the pattern to work you need to identify a column or multiple columns that the source system uses to track change. They would usually be a modified date or sequential identifier. The down side of this pattern is that it doesn&#8217;t detect hard row deletes form the source. That makes it necessary to run a period Full Extract as well.</p></li><li><p><strong>Change Tracking</strong>. The change tracking pattern, uses the Change tracking mechanism of the source database (e.g. Change Tracking in Microsoft SQL Server) to identify change in the source entity and to extract only changed data. The Change Tracking pattern has an advantage over the incremental pattern, in that, it does recognize hard deletes, and is therefore a superior pattern if available.</p></li><li><p><strong>File Pattern</strong>. Extracting data from files is different. There may be multiple files that match a file name pattern. The files also need to be archived after data has been extracted from them. A specialized pattern is required.</p></li><li><p><strong>Date Range Pattern</strong>. The date range pattern is used to extract a subset of the source data based on a date range. The end of the date range is the current batch execution date. The start of the date range is a number of days prior to the current batch effective date. Each time the ETL runs, the current batch effective date, for that batch execution, is set to midnight of the prior day. The date range &#8216;window&#8217; moves forward a day as the current batch effective date changes. To use this pattern, its important that dependent entities further up the chain are also working with the same date range.</p></li></ul><h3><strong>Load</strong></h3><p>Load is the process of loading data from the landing data store into the staging data store. The <strong>staging data store</strong> is typically a database co-located with the Data Warehouse database. It could potentially be the same Database. The staging data store is transient, meaning it doesn&#8217;t persist the data between ETL batch runs. In the case of a Persistent target entity, the staging entity is very short lived, only existing until it has been persisted in Persistent data store.</p><p>It is necessary to stage data for a number of reasons:</p><ul><li><p>Staging places less load on source systems. Extract procedures are keep as simple as possible. The next steps, load, persist, transformation etc may require complex queries, that you don&#8217;t want to run on the source, mission critical, system.</p></li><li><p>If you are combining data from more than 1 source system, then you need to stage data from all those systems before you can combine the data in the transformation step.</p></li><li><p>Staging gives the Data Warehouse the opportunity to implement its own change data capture and data quality screening across source systems.</p></li><li><p>Staging allows more rapid failure recovery, because the data does not need to be Extracted a second time on recovery.</p></li></ul><h3><strong>Persist</strong></h3><p>A Persistent Data Store, store all change history of the source entities. Technically it is a <a href="https://en.wikipedia.org/wiki/Temporal_database">Bi-temporal database</a>. Every row in a Persistent Entity has a Start and End Effective date. Each row is also associated with the an inserted and last updated batch Ids, that are related to a date.</p><ol><li><p>Provides the ability to re-load the data warehouse layer with full history if required (due to a change in logic, model or mistakes).</p></li><li><p>Improves ETL efficiency. It becomes possible to do incremental (delta) loads at all levels.</p></li><li><p>Without Persistent staging, it was difficult to do complex transform logic over the data from incremental extracts into staging tables. These staging tables would, on any given day, only have a small subset of rows from the source table/query. It was impossible to join these tables to other tables to get some other representation of the data that needed more than just the subset that was available.</p></li><li><p>Provides trace-ability and audit-ability of data.</p></li></ol><p>An example of the power of persistent staging is the analysis of the rate of change for scheduled Visits. Scheduling visits across a large complex home care service is complex. This can lead to a lot of schedule and route changes.The persistent layer can capture all these changes and can be used to analyse the rate of schedule &#8220;churn&#8221;. Schedule churn can be very disruptive and ultimately costly to the organisation. In addition, this schedule churn can lead to questions about &#8220;Why did my report change&#8221;. The persistent staging layer provides evidence that the source data is changing, and not the report logic, or a problem with the report.</p><p>The Persistent ETL takes data from the temporary load data store, generates a delta change set if the data has come from a full extract, then applies that change set to the Persistent entity, inserting new versions of rows and end dating existing rows where necessary.</p><h3><strong>Transformation</strong></h3><p>Transformation is the process of transforming the data in either the staging or persistent data stores into the star schema format, and loading it into the Data Warehouse. This is where data staged from multiple source systems is combined into a cohesive set of Facts and Dimensions. There are many techniques required to identify change and implement high performance data loading into the data warehouse. Because it is easy to identify the changed data set from persistent entities, Transform ETL that uses the persistent data store as its source is incremental. Incremental ETL is a design technique for improving ETL throughput.</p><h3><strong>Semantic Layer</strong></h3><p>The Semantic layer is the layer/data store that BI tools connect too. The semantic Layer in the Microsoft world is generally an OLAP Cube, a Tabular model, or a PowerBI data set. There are &#8220;virtual&#8221; semantic layers that pass through queries to the data warehouse. Unless the Data Warehouse is utilizing advanced technology like column stores and MPP, then its likely the queries won&#8217;t execute as quickly as if they aren&#8217;t cached by the semantic layer. The semantic layer is also transient. It is reloaded from the Data Warehouse on regular intervals. The Semantic layer is a high performance <em>aggregated</em> query engine. The emphasis is on aggregated. The mentioned technologies don&#8217;t perform as well on non aggregated queries. Non aggregated queries (like lists of transactions) will perform better when run directly against the data warehouse.</p><h2><strong>Throughput</strong></h2><p>ETL throughput is important especially with large quantities of data. Throughput is generally addressed in 3 ways:</p><ol><li><p>By Design. For example, Incremental extracts are much faster than Full extracts.</p></li><li><p>Through Parallel processing. By splitting the work of a single process over different compute units (e.g. servers) like an MPP database (Azure Data Warehouse).</p></li><li><p>Concurrency. By running multiple processes (i.e. Extract, Load, Persist, Transform) at the same time for different entities. Your Extract is running on-premise using on-premise compute, your load is running on the data lake using poly-base compute, and the Transform is using Azure DW compute.</p></li></ol>]]></content:encoded></item><item><title><![CDATA[Metadata Driven Data Warehouse (MDW) vs Traditional ETL tools]]></title><description><![CDATA[Here at Dimodelo , we are passionate about data warehouses and the benefits they can bring an organisation.]]></description><link>https://dimodelo.substack.com/p/metadata-driven-data-warehouse-mdw-vs-traditional-etl-tools</link><guid isPermaLink="false">https://dimodelo.substack.com/p/metadata-driven-data-warehouse-mdw-vs-traditional-etl-tools</guid><dc:creator><![CDATA[Adam Gilmore]]></dc:creator><pubDate>Mon, 13 Jan 2020 10:02:50 GMT</pubDate><enclosure url="https://substackcdn.com/image/fetch/$s_!Ee_C!,w_256,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F051177eb-7dd5-477a-8799-237c8425c504_216x216.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>Here at Dimodelo , we are passionate about data warehouses and the benefits they can bring an organisation. But we are equally passionate about the art and practice (the how) of building these critical information assets. </p><p>What follows is a comparison of the Metadata Driven approach to Data Warehouse development vs the traditional approach taken with an ETL tool.</p><h3>Introduction to Metadata Driven Data Warehousing</h3><p>A Metadata Driven Data Warehouse (MDW) tool is a class of ETL Tool, designed to improve developer productivity (amongst other things). It&#8217;s a <strong>specialized tool dedicated to Data Warehouse development</strong> <strong>that uses metadata and patterns to deliver data warehouses</strong>, combining modelling, ETL and Orchestration. It works at a logical design level, rather than a physical code level. It captures the design of both the Data Warehouse schema and ETL. It combines the captured design with a set of generation templates to create/sync the data warehouse schema and generate ETL code. The generation templates are pre-defined and tested to create consistent, best practice, quality, and comprehensive code.</p><p>An ETL tool is a general tool that can be applied to different data scenarios like data Warehouse development, Data Integration, System Interoperability, Data Migration. Being generalist makes it flexible, but this flexibility comes at a cost. It requires more architectural input and time consuming manual development from developers. While many ETL tools have GUI front ends, they are essentially the equivalent of programming code for a specific ETL runtime. They work at the detailed code level rather than a logical design level. Working at this low level is time-consuming. They rely on the skills and experience of the developer to ensure best practice, quality, tested and comprehensive code is developed. A considerable effort needs to be expended on defining coding standards, practices, and patterns and ensuring conformance to standards. Most ETL tools only work with the ETL and not the database schema. This means a coordinated deployment is required to manage the schema and ETL.</p><h3>Change Propagation</h3><p>Take a simple example of just changing a column name or data type in a Staging table. This will affect the staging table, the load process that loads the staging table, and any Dimension or Fact transform process that uses the staging table as it&#8217;s source.</p><p><strong>Using a traditional ETL tool, you need to change each of those code artifacts individually</strong>, and then coordinate their deployment to multiple environments. The ETL changes need to be coordinated with the schema changes. This process introduces a lot of effort and potential human error.</p><p>With MDW, the modeling and ETL tools are integrated, and the solution is captured in metadata rather than code, any change that is made to the design propagates throughout the solution. Just change the name/type of the column, and regenerate. All code artifacts are simply regenerated to reflect the change and the tool handles the deployment of both the schema change and ETL code eliminating errors.</p><h3>Portability</h3><p>Data platforms are continually changing. Change is happening at an ever-increasing pace. Keeping up with that change is difficult. ETL code written today is obsolete in 6 months&#8217; time. ETL gets stuck at a point in time, and usually, the only option is to rewrite it to take advantage of the latest technologies.</p><p>Metadata Driven Data Warehousing is different. Because it is not aligned to any one technology, but rather, is captured design at a logical level,<strong> moving from one data platform or technology is as simple as taking an existing project and re-targeting to a different platform</strong>. The code is then re-generating with a new set of generation templates that target that new platform. The ETL patterns remain largely logically the same, but their physical implementation can be very different, utilizing the strengths of different technologies.</p><h3>Productivity/Speed</h3><p>ETL can get complicated quick. Teams can get bogged down in implementation details, and as the body of code grows, <strong>having to maintain and refactor existing code becomes a hinderance to progress</strong>. Defining ETL at a logical mapping level combined with code generation and dedicated data warehousing tooling that lets you import schema and automates mapping increases productivity by a factor of 3. The technical complexity is encapsulated in the generation templates. Developers work at a higher logical level and don&#8217;t get bogged down in writing, deploying, changing and testing ETL code. Change propagation and coordinated deployment mean developers spend more time doing development rather than the admin overhead of releasing code.</p><h3>Cost</h3><p>According to research at Wharton University<strong> the optimum team size for a complex task requiring coordination is 6</strong>&#8230;</p><p>&#8220;if companies are dealing with coordination tasks and motivational issues, and you ask, &#8216;What is your team size and what is optimal?&#8217; that correlates to a team of six. &#8220;Above and beyond five, and you begin to see diminishing motivation,&#8221; says Mueller. &#8220;After the fifth person, you look for cliques. And the number of people who speak at any one time? That&#8217;s harder to manage in a group of five or more.&#8221;</p><p>It&#8217;s a bit more nuanced than that. You can read an article about the research here &#8211; <a href="https://knowledge.wharton.upenn.edu/article/is-your-team-too-big-too-small-whats-the-right-number-2/">https://knowledge.wharton.upenn.edu/article/is-your-team-too-big-too-small-whats-the-right-number-2/</a></p><p>Mostly smaller teams are more productive and, of course, cost less.</p><p>With MDW you empower each team member with tools that make each individual far more productive. Combine that tool productivity with the inherent productivity benefits of small teams (a luxury MDW enables) and you have the recipe for a highly productive team.</p><h3>Consistency</h3><p>Over time data warehouse teams change. Each developer brings their unique approach to ETL code to solve data problems. This can present challenges when the developer leaves or moves on to other tasks. It becomes difficult for others to interpret and understand their code. In the worst cases, it becomes necessary to re-implement.</p><p>With MDW <strong>the design is captured in a consistent way</strong>, prescribed by the tool and architecture adopted. The entire solution is encapsulated in a single solution, easy to find and follow. Even across projects, there is consistency in the approach.</p><p>Not to mention the<strong> consistency of the code</strong> generated by the generation templates that ensure that a small stable of code patterns are judiciously applied to every generated artifact.</p><h3>Quality</h3><p>Code quality is essential to a sustainable data warehouse solution. <strong>Does your code cater for unexpected events?</strong> Does it take an oversimplified approach (e.g. truncate and reload) because other approaches just take too much effort? Is it tested to ensure that every permutation of insert, update, delete and reinstate are catered for? Is it robust? Can it handle duplicates or intra batch changes for example? Can it handle table changes like new columns, or does this mean a reload is required? Is it keeping history? Does it perform? Can it cater for complex transformations? There is a perception that ETL is easy. Just extract data from one place and load it into another. This is what a lot of vendors would like you to believe. The truth is Data Warehouse ETL is complex and requires careful thought. When you examine all the possible use cases, it becomes even more complicated. This complexity also means manually writing robust ETL can be time-consuming and error-prone, even with well thought out patterns.</p><p>The MDW approach is to solve all those complex issues once in the generation template and then apply that to many entities in your project. The template is thoroughly tested to ensure it performs and correctly handles the many use cases. You can have confidence that every generated code artifact has the same high levels of quality.</p><h3>Responsiveness to Business</h3><p>&#8220;The only constant in life is change&#8221;</p><p>That is true for data and reporting. Business requirements and source systems are continually changing, coming, going and upgrading. All the benefits of MDW make your Data Warehouse team much more responsive to a changing environment. Without it, <strong>the team can be very resistant to change</strong> which can result in the business looking for other solutions to their immediate problems.</p><h3>Focus</h3><p>What does this all boil down too? Is your Data Warehouse team lost in the technology or focusing on solving business problems? <strong>Being business-focussed is key to building a powerful information asset</strong> like a data warehouse. Businesses that focus on core business concepts, processes, terms and measures are building a consensus that aids understanding, communication and insight throughout the business. Too often this understanding is concentrated with a few employees and can walk out the door when key employees leave. Having your Data Warehouse team lost in the technical detail, drudgery and churn the ETL, means they have already lost the battle to deliver a long term business-focussed information asset. An MDW lifts the team out of the drudgery and focuses them on the business at hand.</p>]]></content:encoded></item></channel></rss>