Lưu trữ hiệu quả các bộ cặp giá trị khóa với các khóa cực kỳ khác nhau


9

Tôi đã kế thừa một ứng dụng liên kết nhiều loại hoạt động khác nhau với một trang web. Có khoảng 100 loại hoạt động khác nhau và mỗi loại có 3-10 trường khác nhau. Tuy nhiên, tất cả các hoạt động đều có ít nhất một trường ngày (có thể là bất kỳ sự kết hợp nào giữa ngày, ngày bắt đầu, ngày kết thúc, ngày bắt đầu dự kiến, v.v.) và một trường người có trách nhiệm. Tất cả các trường khác rất khác nhau và trường ngày bắt đầu sẽ không nhất thiết được gọi là "Ngày bắt đầu".

Tạo một bảng phụ cho mỗi loại hoạt động sẽ dẫn đến một lược đồ với 100 bảng phụ khác nhau, điều này sẽ quá khó để xử lý. Giải pháp hiện tại cho vấn đề này là lưu trữ các giá trị hoạt động dưới dạng cặp khóa-giá trị. Đây là một lược đồ được đơn giản hóa rất nhiều của hệ thống hiện tại để có được điểm.

nhập mô tả hình ảnh ở đây

Mỗi Activity có nhiều ActivityFields; mỗi Trang web có nhiều Hoạt động và bảng SiteActivityData lưu trữ KVP cho mỗi SiteActivity.

Điều này làm cho ứng dụng (dựa trên web) rất dễ mã hóa bởi vì tất cả những gì bạn thực sự cần làm là lặp lại các bản ghi trong SiteActivityData cho một hoạt động nhất định và thêm nhãn và điều khiển đầu vào cho mỗi hàng vào một biểu mẫu. Nhưng có rất nhiều vấn đề:

  • Liêm chính là xấu; có thể đặt một trường trong SiteActivityData không thuộc loại hoạt động và DataValue là trường varchar nên số và ngày cần phải được liên tục truyền.
  • Báo cáo và truy vấn đặc biệt của dữ liệu này là khó khăn, dễ bị lỗi và chậm. Ví dụ: để có được một danh sách tất cả các hoạt động của một loại nhất định có Ngày kết thúc trong một phạm vi được chỉ định, cần có các trục xoay và chuyển các biến thành các ngày. Các nhà văn báo cáo ghét lược đồ này, và tôi không đổ lỗi cho họ.

Vì vậy, những gì tôi đang tìm kiếm là một cách để lưu trữ một số lượng lớn các hoạt động gần như không có trường chung theo cách làm cho báo cáo dễ dàng hơn. Những gì tôi đã nghĩ ra cho đến nay là sử dụng XML để lưu trữ dữ liệu hoạt động theo định dạng giả:

nhập mô tả hình ảnh ở đây

Bảng Activity sẽ chứa XSD cho từng hoạt động, loại bỏ sự cần thiết của bảng ActivityField. SiteActivity sẽ chứa XML giá trị khóa để mỗi hoạt động cho một trang web sẽ nằm trong một hàng.

Một hoạt động sẽ trông giống như thế này (nhưng tôi chưa hoàn thành nó):

<SomeActivityType>
  <SomeDateField type="StartDate">2000-01-01</SomeDateField>
  <AnotherDateField type="EndDate">2011-01-01</AnotherDateField>
  <EmployeeId type="ResponsiblePerson">1234</EmployeeId>
  <SomeTextField>blah blah</SomeTextField>
  ...

Ưu điểm:

  • XSD sẽ xác thực XML, bắt các lỗi như đặt một chuỗi vào trường số ở cấp cơ sở dữ liệu, một điều không thể với lược đồ cũ lưu trữ mọi thứ trong varchar.
  • Các bản ghi của KVP được sử dụng để xây dựng các biểu mẫu web có thể dễ dàng được sao chép bằng cách sử dụng select ... from ActivityXML.nodes('/SomeActivityType/*') as T(r)
  • Một truy vấn con xpath của XML có thể được sử dụng để tạo ra một tập kết quả có các cột cho ngày bắt đầu, ngày kết thúc, v.v. mà không cần sử dụng một trục, đại loại như select ActivityXML.value('.[@type=StartDate]', 'datetime') as StartDate, ActivityXML.value('.[@type=EndDate]', 'datetime') as EndDate from SiteActivity where...

Điều này có vẻ như là một ý tưởng tốt? Tôi không thể nghĩ ra những cách khác để lưu trữ một số lượng lớn các bộ tài sản khác nhau như vậy. Một suy nghĩ khác mà tôi đã có là giữ lược đồ hiện có và dịch nó thành một thứ dễ truy cập hơn trong kho dữ liệu, nhưng tôi chưa bao giờ thiết kế một lược đồ sao trước đây và sẽ không biết bắt đầu từ đâu.

Câu hỏi bổ sung: Nếu tôi xác định thẻ có kiểu dữ liệu ngày trong XSD bằng cách sử dụng xs:date, SQL Server sẽ lập chỉ mục đó dưới dạng giá trị ngày? Tôi lo ngại nếu tôi truy vấn theo ngày, nó sẽ cần truyền chuỗi ngày thành giá trị ngày và thổi bay mọi cơ hội sử dụng chỉ mục.


Làm thế nào để cập nhật dữ liệu cho các báo cáo cần phải được? Các báo cáo sẽ được sản xuất?
James Anderson

Hầu hết các báo cáo đều đạt được kho dữ liệu ngay bây giờ (không thực sự là DW, về cơ bản nó là bản sao của lược đồ giao dịch sản xuất với một loạt các khung nhìn và bảng từ các cơ sở dữ liệu khác được thêm vào). Có báo cáo là một ngày hết hạn là chấp nhận được, nhưng nó sẽ là một phần thưởng nếu nó có thể được sống.
Paul Abbott

Có bao nhiêu sự chồng chéo trong các lĩnh vực? Có mười trường bao gồm tất cả 100 kiểu con, hoặc có ~ 500 trường hoàn toàn khác nhau?
Jon của tất cả các giao dịch

Có 72 trường và 75 loại hoạt động. 30 trường chỉ được sử dụng bởi một hoạt động và hầu hết các trường còn lại được sử dụng bởi 5-10 hoạt động. Có một số lĩnh vực được sử dụng bởi ~ 30 hoạt động khác nhau. Đối với hầu hết các phần, không có nhiều điểm chung giữa các hoạt động.
Paul Abbott

Câu trả lời:


7

Vì vậy, những gì tôi đang tìm kiếm là một cách để lưu trữ một số lượng lớn các hoạt động gần như không có trường chung theo cách làm cho báo cáo dễ dàng hơn.

Không đủ đại diện để bình luận đầu tiên, vì vậy chúng tôi đi đây!

Nếu mục đích chính là báo cáo và bạn có DW (ngay cả khi đó không phải là lược đồ sao), tôi khuyên bạn nên cố gắng đưa mục tiêu này vào lược đồ sao. Những lợi ích là nhanh chóng, truy vấn đơn giản. Nhược điểm là ETL, nhưng bạn đã xem xét việc chuyển dữ liệu sang thiết kế mới và lược đồ ETL sang sao có thể đơn giản hơn để xây dựng và duy trì so với giải pháp trình bao bọc XML (và SSIS được bao gồm trong giấy phép SQL Server của bạn). Thêm vào đó, nó bắt đầu quá trình thiết kế báo cáo / phân tích được công nhận.

Vậy làm thế nào để làm điều đó ... Có vẻ như bạn có cái được gọi là Sự thật Không có thật . Đây là giao điểm của các thuộc tính xác định sự kiện không có thước đo liên quan (chẳng hạn như giá bán). Bạn có ngày có sẵn cho một số hoặc tất cả các hoạt động của bạn? Có khả năng bạn thực sự nên có một giao điểm của một Hoạt động, Trang web và (các) Ngày.

DimActivity- Tôi đoán có một mô hình, một cái gì đó có thể cho phép bạn chia chúng thành ít nhất là các cột được chia sẻ tương đối. Nếu vậy, bạn có thể có ba? số năm? kích thước cho các lớp hoạt động. Tệ nhất là bạn có một vài cột nhất quán, chẳng hạn như tên hoạt động, bạn có thể lọc và bạn để lại các tiêu đề chung như "Thuộc tính1", v.v. cho các chi tiết ngẫu nhiên còn lại.

Bạn không cần mọi thứ trong thứ nguyên - ở đó (có thể) không nên có bất kỳ ngày nào trong thứ nguyên Hoạt động - tất cả chúng đều có trong thực tế, như các tham chiếu chính của Surrogate cho thứ nguyên Ngày. Ví dụ: Ngày tồn tại trong một chiều người sẽ là ngày sinh vì đó là thuộc tính của một người. Một ngày đến bệnh viện sẽ nằm trong thực tế, vì đó là một sự kiện thời gian liên quan đến một người, trong số những thứ khác, nhưng nó không phải là một thuộc tính của người đến bệnh viện. Thêm ngày thảo luận trong thực tế.

DimSite- có vẻ thẳng tiến, vì vậy chúng tôi sẽ mô tả Khóa thay thế ở đây. Thực chất đây chỉ là một ID gia tăng, duy nhất. Cột số nguyên là phổ biến. Điều này cho phép tách DW và hệ thống nguồn và đảm bảo các phép nối tối ưu trong kho dữ liệu. Khóa tự nhiên hoặc Khóa doanh nghiệp của bạn thường được lưu giữ, nhưng để bảo trì / thiết kế không phân tích và tham gia. Lược đồ ví dụ:

CREATE TABLE [DIM].[Site]
(
 SiteSK INT NOT NULL IDENTITY PRIMARY KEY
,SiteNK INT NOT NULL --source system key
,SiteName VARCHAR(500) NOT NULL
)

DimDate- thuộc tính ngày. Tạo một "chìa khóa thông minh" thay vì Danh tính. Điều này có nghĩa là bạn có thể nhập một số nguyên có ý nghĩa liên quan đến ngày cho các truy vấn, chẳng hạn như WHERE DateSK = 20150708. Có rất nhiều tập lệnh miễn phí để tải DimDate và hầu hết đều có khóa thông minh này. ( một lựa chọn )

DimEmployee - XML ​​của bạn bao gồm điều này, nếu đó là thay đổi chung hơn đối với DimPerson và điền vào các thuộc tính người có liên quan khi chúng có sẵn và thích hợp để báo cáo.

Và sự thật của bạn là:

FactActivitySite
DimSiteSK - FK to DimSite
DimActivitySK - FK to DimActivity
DimEmployee - FK to DimEmployee
DimDateSK - FK to DimDate

Bạn có thể Đổi tên chúng trong Sự kiện và bạn có thể có nhiều khóa ngày cho mỗi sự kiện. Sự kiện thường rất lớn nên việc tránh cập nhật thường tốt ... nếu bạn có nhiều cập nhật ngày cho một sự kiện, bạn có thể muốn thử thiết kế Xóa / Chèn bằng cách thêm SK vào thực tế cho phép chọn hàng "cập nhật" vào bị xóa sau đó chèn dữ liệu mới nhất.

Mở rộng ngày thực tế của bạn đến bất cứ điều gì bạn cần : StartDateSK, EndDateSK, ScheduledStartDateSK.

Tất cả các kích thước phải có một hàng Không xác định thường có mã SK1 -1 được mã hóa cứng. Khi bạn tải thực tế và một hoạt động không có bất kỳ Ngày nào được bao gồm, nó chỉ cần tải -1.

Thực tế là một tập hợp các tham chiếu số nguyên cho các thuộc tính của bạn được lưu trữ trong các kích thước, nối chúng lại với nhau và bạn có được tất cả các chi tiết của mình, trong một mẫu liên kết rất rõ ràng và thực tế, do các loại dữ liệu của nó, đặc biệt nhỏ và nhanh. Vì bạn đang ở trong SQL Server, hãy thêm một chỉ mục cột để tăng hiệu suất hơn nữa. Bạn chỉ có thể thả nó và xây dựng lại trong ETL. Khi bạn nhận được SQL 2014+, bạn có thể ghi vào các chỉ mục của cột.

nhập mô tả hình ảnh ở đây

Nếu bạn đi tuyến đường này nghiên cứu Mô hình chiều. Tôi muốn giới thiệu phương pháp Kimball . Ngoài ra còn có rất nhiều hướng dẫn miễn phí, nhưng nếu đây sẽ là bất cứ điều gì khác ngoài giải pháp một lần, khoản đầu tư có khả năng đáng giá.


(câu hỏi từ wesdev): @Dave, bạn đã sử dụng công cụ ERD nào?
ypercubeᵀᴹ

Điều này đã được thực hiện trong Microsoft Visio 2013
Dave
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.