diff --git a/gooddata-fdw/tests/import_foreign_schema/fixtures/import_compute_without_restrictions.yaml b/gooddata-fdw/tests/import_foreign_schema/fixtures/import_compute_without_restrictions.yaml index 7dc3ac0e1..a2aa63137 100644 --- a/gooddata-fdw/tests/import_foreign_schema/fixtures/import_compute_without_restrictions.yaml +++ b/gooddata-fdw/tests/import_foreign_schema/fixtures/import_compute_without_restrictions.yaml @@ -19,55 +19,35 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - - '19939' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' + - '19974' Content-Type: - application/vnd.gooddata.api+json DATE: &id001 - PLACEHOLDER Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: data: @@ -537,10 +517,10 @@ interactions: type: dataset labels: data: - - id: state - type: label - id: geo__state__location type: label + - id: state + type: label links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/state meta: @@ -623,38 +603,38 @@ interactions: sourceColumns: null sourceColumnDataTypes: null - identifier: - id: customers + id: campaigns type: dataset multivalue: false sources: - - column: customer_id + - column: campaign_id dataType: INT target: - id: customer_id + id: campaign_id type: attribute sourceColumns: null sourceColumnDataTypes: null - identifier: - id: products + id: customers type: dataset multivalue: false sources: - - column: product_id + - column: customer_id dataType: INT target: - id: product_id + id: customer_id type: attribute sourceColumns: null sourceColumnDataTypes: null - identifier: - id: campaigns + id: products type: dataset multivalue: false sources: - - column: campaign_id + - column: product_id dataType: INT target: - id: campaign_id + id: product_id type: attribute sourceColumns: null sourceColumnDataTypes: null @@ -890,6 +870,7 @@ interactions: primary: false sourceColumn: geo__state__location sourceColumnDataType: STRING + valueType: GEO links: self: http://localhost:3000/api/v1/entities/workspaces/demo/labels/geo__state__location - id: product_id @@ -939,6 +920,7 @@ interactions: type: dataset attributes: title: Date + description: '' tags: - Date type: DATE @@ -1012,7 +994,7 @@ interactions: next: http://localhost:3000/api/v1/entities/workspaces/demo/attributes?include=labels%2Cdatasets&page=1&size=500 - request: method: GET - uri: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts&page=0&size=500 + uri: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts%2CaggregatedFacts&page=0&size=500 body: null headers: Accept: @@ -1028,54 +1010,34 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - - '12092' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' + - '12145' Content-Type: - application/vnd.gooddata.api+json DATE: *id001 Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: data: @@ -1195,6 +1157,7 @@ interactions: type: dataset attributes: title: Date + description: '' tags: - Date areRelationsValid: true @@ -1204,12 +1167,12 @@ interactions: data: - id: date.day type: attribute + - id: date.week + type: attribute - id: date.month type: attribute - id: date.quarter type: attribute - - id: date.week - type: attribute - id: date.year type: attribute links: @@ -1242,38 +1205,38 @@ interactions: sourceColumns: null sourceColumnDataTypes: null - identifier: - id: customers + id: campaigns type: dataset multivalue: false sources: - - column: customer_id + - column: campaign_id dataType: INT target: - id: customer_id + id: campaign_id type: attribute sourceColumns: null sourceColumnDataTypes: null - identifier: - id: products + id: customers type: dataset multivalue: false sources: - - column: product_id + - column: customer_id dataType: INT target: - id: product_id + id: customer_id type: attribute sourceColumns: null sourceColumnDataTypes: null - identifier: - id: campaigns + id: products type: dataset multivalue: false sources: - - column: campaign_id + - column: product_id dataType: INT target: - id: campaign_id + id: product_id type: attribute sourceColumns: null sourceColumnDataTypes: null @@ -1612,8 +1575,8 @@ interactions: links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/order_line_id links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts&page=0&size=500 - next: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts&page=1&size=500 + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts%2CaggregatedFacts&page=0&size=500 + next: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts%2CaggregatedFacts&page=1&size=500 - request: method: GET uri: http://localhost:3000/api/v1/entities/workspaces/demo/metrics?page=0&size=500 @@ -1632,54 +1595,34 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - '10543' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' Content-Type: - application/vnd.gooddata.api+json DATE: *id001 Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: data: @@ -1688,7 +1631,7 @@ interactions: attributes: title: '# of Active Customers' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0' maql: SELECT COUNT({attribute/customer_id},{attribute/order_line_id}) @@ -1703,7 +1646,7 @@ interactions: attributes: title: '# of Orders' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0' maql: SELECT COUNT({attribute/order_id}) @@ -1718,7 +1661,7 @@ interactions: attributes: title: '# of Top Customers' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0' maql: 'SELECT {metric/amount_of_active_customers} WHERE (SELECT @@ -1735,7 +1678,7 @@ interactions: title: '# of Valid Orders' description: '' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.00' maql: SELECT {metric/amount_of_orders} WHERE NOT ({label/order_status} @@ -1751,7 +1694,7 @@ interactions: attributes: title: Campaign Spend areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT SUM({fact/spend}) @@ -1766,7 +1709,7 @@ interactions: attributes: title: Order Amount areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT SUM({fact/price}*{fact/quantity}) @@ -1781,7 +1724,7 @@ interactions: attributes: title: '% Revenue' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.0%' maql: SELECT {metric/revenue} / {metric/total_revenue} @@ -1796,7 +1739,7 @@ interactions: attributes: title: '% Revenue from Top 10 Customers' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.0%' maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10}\ @@ -1812,7 +1755,7 @@ interactions: attributes: title: '% Revenue from Top 10% Customers' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.0%' maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10_percent}\ @@ -1828,7 +1771,7 @@ interactions: attributes: title: '% Revenue from Top 10% Products' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.0%' maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10_percent}\ @@ -1844,7 +1787,7 @@ interactions: attributes: title: '% Revenue from Top 10 Products' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.0%' maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10}\ @@ -1860,7 +1803,7 @@ interactions: attributes: title: '% Revenue in Category' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.0%' maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY {attribute/products.category}, @@ -1876,7 +1819,7 @@ interactions: attributes: title: '% Revenue per Product' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.0%' maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY ALL @@ -1893,7 +1836,7 @@ interactions: title: Revenue description: '' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/order_amount} WHERE NOT ({label/order_status} @@ -1909,7 +1852,7 @@ interactions: attributes: title: Revenue (Clothing) areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/revenue} WHERE {label/products.category} IN @@ -1925,7 +1868,7 @@ interactions: attributes: title: Revenue (Electronic) areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/revenue} WHERE {label/products.category} IN @@ -1941,7 +1884,7 @@ interactions: attributes: title: Revenue (Home) areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/revenue} WHERE {label/products.category} IN @@ -1957,7 +1900,7 @@ interactions: attributes: title: Revenue (Outdoor) areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/revenue} WHERE {label/products.category} IN @@ -1973,7 +1916,7 @@ interactions: attributes: title: Revenue per Customer areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0.0 maql: SELECT AVG(SELECT {metric/revenue} BY {attribute/customer_id}) @@ -1988,7 +1931,7 @@ interactions: attributes: title: Revenue per Dollar Spent areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0.0 maql: SELECT {metric/revenue} / {metric/campaign_spend} @@ -2003,7 +1946,7 @@ interactions: attributes: title: Revenue / Top 10 areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/revenue} WHERE TOP(10) OF ({metric/revenue}) @@ -2018,7 +1961,7 @@ interactions: attributes: title: Revenue / Top 10% areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/revenue} WHERE TOP(10%) OF ({metric/revenue}) @@ -2033,7 +1976,7 @@ interactions: attributes: title: Total Revenue areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/revenue} BY ALL OTHER @@ -2048,7 +1991,7 @@ interactions: attributes: title: Total Revenue (No Filters) areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/total_revenue} WITHOUT PARENT FILTER diff --git a/gooddata-fdw/tests/import_foreign_schema/fixtures/import_insights_without_restrictions.yaml b/gooddata-fdw/tests/import_foreign_schema/fixtures/import_insights_without_restrictions.yaml index b2f880220..c5dc208f0 100644 --- a/gooddata-fdw/tests/import_foreign_schema/fixtures/import_insights_without_restrictions.yaml +++ b/gooddata-fdw/tests/import_foreign_schema/fixtures/import_insights_without_restrictions.yaml @@ -19,55 +19,35 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - - '19939' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' + - '19974' Content-Type: - application/vnd.gooddata.api+json DATE: &id001 - PLACEHOLDER Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: data: @@ -537,10 +517,10 @@ interactions: type: dataset labels: data: - - id: state - type: label - id: geo__state__location type: label + - id: state + type: label links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/state meta: @@ -623,38 +603,38 @@ interactions: sourceColumns: null sourceColumnDataTypes: null - identifier: - id: customers + id: campaigns type: dataset multivalue: false sources: - - column: customer_id + - column: campaign_id dataType: INT target: - id: customer_id + id: campaign_id type: attribute sourceColumns: null sourceColumnDataTypes: null - identifier: - id: products + id: customers type: dataset multivalue: false sources: - - column: product_id + - column: customer_id dataType: INT target: - id: product_id + id: customer_id type: attribute sourceColumns: null sourceColumnDataTypes: null - identifier: - id: campaigns + id: products type: dataset multivalue: false sources: - - column: campaign_id + - column: product_id dataType: INT target: - id: campaign_id + id: product_id type: attribute sourceColumns: null sourceColumnDataTypes: null @@ -890,6 +870,7 @@ interactions: primary: false sourceColumn: geo__state__location sourceColumnDataType: STRING + valueType: GEO links: self: http://localhost:3000/api/v1/entities/workspaces/demo/labels/geo__state__location - id: product_id @@ -939,6 +920,7 @@ interactions: type: dataset attributes: title: Date + description: '' tags: - Date type: DATE @@ -1012,7 +994,7 @@ interactions: next: http://localhost:3000/api/v1/entities/workspaces/demo/attributes?include=labels%2Cdatasets&page=1&size=500 - request: method: GET - uri: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts&page=0&size=500 + uri: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts%2CaggregatedFacts&page=0&size=500 body: null headers: Accept: @@ -1028,54 +1010,34 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - - '12092' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' + - '12145' Content-Type: - application/vnd.gooddata.api+json DATE: *id001 Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: data: @@ -1195,6 +1157,7 @@ interactions: type: dataset attributes: title: Date + description: '' tags: - Date areRelationsValid: true @@ -1204,12 +1167,12 @@ interactions: data: - id: date.day type: attribute + - id: date.week + type: attribute - id: date.month type: attribute - id: date.quarter type: attribute - - id: date.week - type: attribute - id: date.year type: attribute links: @@ -1242,38 +1205,38 @@ interactions: sourceColumns: null sourceColumnDataTypes: null - identifier: - id: customers + id: campaigns type: dataset multivalue: false sources: - - column: customer_id + - column: campaign_id dataType: INT target: - id: customer_id + id: campaign_id type: attribute sourceColumns: null sourceColumnDataTypes: null - identifier: - id: products + id: customers type: dataset multivalue: false sources: - - column: product_id + - column: customer_id dataType: INT target: - id: product_id + id: customer_id type: attribute sourceColumns: null sourceColumnDataTypes: null - identifier: - id: campaigns + id: products type: dataset multivalue: false sources: - - column: campaign_id + - column: product_id dataType: INT target: - id: campaign_id + id: product_id type: attribute sourceColumns: null sourceColumnDataTypes: null @@ -1612,8 +1575,8 @@ interactions: links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/order_line_id links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts&page=0&size=500 - next: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts&page=1&size=500 + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts%2CaggregatedFacts&page=0&size=500 + next: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts%2CaggregatedFacts&page=1&size=500 - request: method: GET uri: http://localhost:3000/api/v1/entities/workspaces/demo/metrics?page=0&size=500 @@ -1632,54 +1595,34 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - '10543' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' Content-Type: - application/vnd.gooddata.api+json DATE: *id001 Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: data: @@ -1688,7 +1631,7 @@ interactions: attributes: title: '# of Active Customers' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0' maql: SELECT COUNT({attribute/customer_id},{attribute/order_line_id}) @@ -1703,7 +1646,7 @@ interactions: attributes: title: '# of Orders' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0' maql: SELECT COUNT({attribute/order_id}) @@ -1718,7 +1661,7 @@ interactions: attributes: title: '# of Top Customers' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0' maql: 'SELECT {metric/amount_of_active_customers} WHERE (SELECT @@ -1735,7 +1678,7 @@ interactions: title: '# of Valid Orders' description: '' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.00' maql: SELECT {metric/amount_of_orders} WHERE NOT ({label/order_status} @@ -1751,7 +1694,7 @@ interactions: attributes: title: Campaign Spend areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT SUM({fact/spend}) @@ -1766,7 +1709,7 @@ interactions: attributes: title: Order Amount areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT SUM({fact/price}*{fact/quantity}) @@ -1781,7 +1724,7 @@ interactions: attributes: title: '% Revenue' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.0%' maql: SELECT {metric/revenue} / {metric/total_revenue} @@ -1796,7 +1739,7 @@ interactions: attributes: title: '% Revenue from Top 10 Customers' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.0%' maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10}\ @@ -1812,7 +1755,7 @@ interactions: attributes: title: '% Revenue from Top 10% Customers' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.0%' maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10_percent}\ @@ -1828,7 +1771,7 @@ interactions: attributes: title: '% Revenue from Top 10% Products' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.0%' maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10_percent}\ @@ -1844,7 +1787,7 @@ interactions: attributes: title: '% Revenue from Top 10 Products' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.0%' maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10}\ @@ -1860,7 +1803,7 @@ interactions: attributes: title: '% Revenue in Category' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.0%' maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY {attribute/products.category}, @@ -1876,7 +1819,7 @@ interactions: attributes: title: '% Revenue per Product' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.0%' maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY ALL @@ -1893,7 +1836,7 @@ interactions: title: Revenue description: '' areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/order_amount} WHERE NOT ({label/order_status} @@ -1909,7 +1852,7 @@ interactions: attributes: title: Revenue (Clothing) areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/revenue} WHERE {label/products.category} IN @@ -1925,7 +1868,7 @@ interactions: attributes: title: Revenue (Electronic) areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/revenue} WHERE {label/products.category} IN @@ -1941,7 +1884,7 @@ interactions: attributes: title: Revenue (Home) areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/revenue} WHERE {label/products.category} IN @@ -1957,7 +1900,7 @@ interactions: attributes: title: Revenue (Outdoor) areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/revenue} WHERE {label/products.category} IN @@ -1973,7 +1916,7 @@ interactions: attributes: title: Revenue per Customer areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0.0 maql: SELECT AVG(SELECT {metric/revenue} BY {attribute/customer_id}) @@ -1988,7 +1931,7 @@ interactions: attributes: title: Revenue per Dollar Spent areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0.0 maql: SELECT {metric/revenue} / {metric/campaign_spend} @@ -2003,7 +1946,7 @@ interactions: attributes: title: Revenue / Top 10 areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/revenue} WHERE TOP(10) OF ({metric/revenue}) @@ -2018,7 +1961,7 @@ interactions: attributes: title: Revenue / Top 10% areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/revenue} WHERE TOP(10%) OF ({metric/revenue}) @@ -2033,7 +1976,7 @@ interactions: attributes: title: Total Revenue areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/revenue} BY ALL OTHER @@ -2048,7 +1991,7 @@ interactions: attributes: title: Total Revenue (No Filters) areRelationsValid: true - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/total_revenue} WITHOUT PARENT FILTER @@ -2079,54 +2022,34 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - - '32984' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' + - '33000' Content-Type: - application/vnd.gooddata.api+json DATE: *id001 Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: data: @@ -2193,7 +2116,7 @@ interactions: position: bottom version: '2' visualizationUrl: local:treemap - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 relationships: createdBy: data: @@ -2264,9 +2187,9 @@ interactions: identifier: id: date type: dataset - from: -12 + from: -11 granularity: GDC.time.month - to: -1 + to: 0 properties: controls: colorMapping: @@ -2292,7 +2215,7 @@ interactions: rotation: auto version: '2' visualizationUrl: local:combo2 - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 relationships: createdBy: data: @@ -2318,90 +2241,6 @@ interactions: origin: originType: NATIVE originId: demo - - id: percentage_of_customers_by_region - type: visualizationObject - attributes: - title: Percentage of Customers by Region - areRelationsValid: true - content: - buckets: - - items: - - measure: - definition: - measureDefinition: - filters: [] - item: - identifier: - id: amount_of_active_customers - type: metric - localIdentifier: 1a14cdc1293c46e89a2e25d3e741d235 - title: '# of Active Customers' - localIdentifier: measures - - items: - - attribute: - displayForm: - identifier: - id: date.month - type: label - localIdentifier: c1feca1864244ec2ace7a9b9d7fda231 - localIdentifier: view - - items: - - attribute: - displayForm: - identifier: - id: region - type: label - localIdentifier: 530cddbd7ca04d039e73462d81ed44d5 - localIdentifier: stack - filters: - - negativeAttributeFilter: - displayForm: - identifier: - id: region - type: label - notIn: - values: [] - - relativeDateFilter: - dataSet: - identifier: - id: date - type: dataset - from: -11 - granularity: GDC.time.month - to: 0 - properties: - controls: - legend: - position: bottom - stackMeasuresToPercent: true - version: '2' - visualizationUrl: local:area - createdAt: 2025-08-07 10:53 - relationships: - createdBy: - data: - id: admin - type: userIdentifier - metrics: - data: - - id: amount_of_active_customers - type: metric - datasets: - data: - - id: date - type: dataset - labels: - data: - - id: date.month - type: label - - id: region - type: label - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/visualizationObjects/percentage_of_customers_by_region - meta: - origin: - originType: NATIVE - originId: demo - id: percent_revenue_per_product_by_customer_and_category type: visualizationObject attributes: @@ -2480,7 +2319,7 @@ interactions: direction: asc version: '2' visualizationUrl: local:table - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 relationships: createdBy: data: @@ -2506,6 +2345,90 @@ interactions: origin: originType: NATIVE originId: demo + - id: percentage_of_customers_by_region + type: visualizationObject + attributes: + title: Percentage of Customers by Region + areRelationsValid: true + content: + buckets: + - items: + - measure: + definition: + measureDefinition: + filters: [] + item: + identifier: + id: amount_of_active_customers + type: metric + localIdentifier: 1a14cdc1293c46e89a2e25d3e741d235 + title: '# of Active Customers' + localIdentifier: measures + - items: + - attribute: + displayForm: + identifier: + id: date.month + type: label + localIdentifier: c1feca1864244ec2ace7a9b9d7fda231 + localIdentifier: view + - items: + - attribute: + displayForm: + identifier: + id: region + type: label + localIdentifier: 530cddbd7ca04d039e73462d81ed44d5 + localIdentifier: stack + filters: + - negativeAttributeFilter: + displayForm: + identifier: + id: region + type: label + notIn: + values: [] + - relativeDateFilter: + dataSet: + identifier: + id: date + type: dataset + from: -11 + granularity: GDC.time.month + to: 0 + properties: + controls: + legend: + position: bottom + stackMeasuresToPercent: true + version: '2' + visualizationUrl: local:area + createdAt: 2025-09-03 13:55 + relationships: + createdBy: + data: + id: admin + type: userIdentifier + metrics: + data: + - id: amount_of_active_customers + type: metric + datasets: + data: + - id: date + type: dataset + labels: + data: + - id: date.month + type: label + - id: region + type: label + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/visualizationObjects/percentage_of_customers_by_region + meta: + origin: + originType: NATIVE + originId: demo - id: product_breakdown type: visualizationObject attributes: @@ -2562,7 +2485,7 @@ interactions: position: bottom version: '2' visualizationUrl: local:treemap - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 relationships: createdBy: data: @@ -2636,7 +2559,7 @@ interactions: position: bottom version: '2' visualizationUrl: local:donut - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 relationships: createdBy: data: @@ -2732,7 +2655,7 @@ interactions: visible: false version: '2' visualizationUrl: local:column - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 relationships: createdBy: data: @@ -2818,7 +2741,7 @@ interactions: enabled: true version: '2' visualizationUrl: local:scatter - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 relationships: createdBy: data: @@ -2938,7 +2861,7 @@ interactions: direction: asc version: '2' visualizationUrl: local:table - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 relationships: createdBy: data: @@ -3025,7 +2948,7 @@ interactions: position: bottom version: '2' visualizationUrl: local:line - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 relationships: createdBy: data: @@ -3089,7 +3012,7 @@ interactions: properties: {} version: '2' visualizationUrl: local:bar - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 relationships: createdBy: data: @@ -3164,7 +3087,7 @@ interactions: min: '0' version: '2' visualizationUrl: local:scatter - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 relationships: createdBy: data: @@ -3253,7 +3176,7 @@ interactions: rotation: auto version: '2' visualizationUrl: local:combo2 - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 relationships: createdBy: data: @@ -3335,7 +3258,7 @@ interactions: position: bottom version: '2' visualizationUrl: local:bar - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 relationships: createdBy: data: @@ -3413,7 +3336,7 @@ interactions: position: bottom version: '2' visualizationUrl: local:bar - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 relationships: createdBy: data: @@ -3440,7 +3363,7 @@ interactions: type: metric attributes: title: '# of Orders' - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0' maql: SELECT COUNT({attribute/order_id}) @@ -3451,7 +3374,7 @@ interactions: attributes: title: Revenue description: '' - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/order_amount} WHERE NOT ({label/order_status} @@ -3509,7 +3432,7 @@ interactions: type: metric attributes: title: '% Revenue in Category' - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.0%' maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY {attribute/products.category}, @@ -3520,7 +3443,7 @@ interactions: type: metric attributes: title: Revenue per Customer - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0.0 maql: SELECT AVG(SELECT {metric/revenue} BY {attribute/customer_id}) @@ -3530,7 +3453,7 @@ interactions: type: metric attributes: title: Revenue / Top 10 - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT {metric/revenue} WHERE TOP(10) OF ({metric/revenue}) @@ -3551,7 +3474,7 @@ interactions: type: metric attributes: title: '% Revenue per Product' - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0.0%' maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY ALL @@ -3578,6 +3501,7 @@ interactions: type: dataset attributes: title: Date + description: '' tags: - Date type: DATE @@ -3652,7 +3576,7 @@ interactions: type: metric attributes: title: '# of Active Customers' - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: '#,##0' maql: SELECT COUNT({attribute/customer_id},{attribute/order_line_id}) @@ -3675,7 +3599,7 @@ interactions: type: metric attributes: title: Campaign Spend - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0 maql: SELECT SUM({fact/spend}) @@ -3685,7 +3609,7 @@ interactions: type: metric attributes: title: Revenue per Dollar Spent - createdAt: 2025-08-07 10:53 + createdAt: 2025-09-03 13:55 content: format: $#,##0.0 maql: SELECT {metric/revenue} / {metric/campaign_spend} diff --git a/gooddata-sdk/gooddata_sdk/catalog/entity.py b/gooddata-sdk/gooddata_sdk/catalog/entity.py index be3eadf07..141ef6919 100644 --- a/gooddata-sdk/gooddata_sdk/catalog/entity.py +++ b/gooddata-sdk/gooddata_sdk/catalog/entity.py @@ -11,7 +11,7 @@ from gooddata_sdk.catalog.base import Base, JsonApiEntityBase from gooddata_sdk.compute.model.base import ObjId -from gooddata_sdk.utils import AllPagedEntities +from gooddata_sdk.utils import AllPagedEntities, safeget_list T = TypeVar("T", bound="AttrCatalogEntity") @@ -84,6 +84,10 @@ def from_api( def client_class() -> Any: return NotImplemented + def _relation_entity_from_side_loads(self, entity: builtins.type[T], path: list[str]) -> list[T]: + related_fact_ids = [(x.get("id"), x.get("type")) for x in safeget_list(self.json_api_relationships, path)] + return [entity.from_api(sl) for sl in self.json_api_side_loads if (sl["id"], sl["type"]) in related_fact_ids] + class CatalogEntity: def __init__(self, entity: dict[str, Any]) -> None: diff --git a/gooddata-sdk/gooddata_sdk/catalog/workspace/content_service.py b/gooddata-sdk/gooddata_sdk/catalog/workspace/content_service.py index 99e130bfd..4acc65c7f 100644 --- a/gooddata-sdk/gooddata_sdk/catalog/workspace/content_service.py +++ b/gooddata-sdk/gooddata_sdk/catalog/workspace/content_service.py @@ -79,7 +79,7 @@ def get_full_catalog(self, workspace_id: str, inject_valid_objects_func: bool = get_datasets = functools.partial( self._entities_api.get_all_entities_datasets, workspace_id, - include=["attributes", "facts"], + include=["attributes", "facts", "aggregatedFacts"], _check_return_type=False, ) diff --git a/gooddata-sdk/gooddata_sdk/catalog/workspace/declarative_model/workspace/logical_model/dataset/dataset.py b/gooddata-sdk/gooddata_sdk/catalog/workspace/declarative_model/workspace/logical_model/dataset/dataset.py index 3f5b4be3a..deda48af1 100644 --- a/gooddata-sdk/gooddata_sdk/catalog/workspace/declarative_model/workspace/logical_model/dataset/dataset.py +++ b/gooddata-sdk/gooddata_sdk/catalog/workspace/declarative_model/workspace/logical_model/dataset/dataset.py @@ -43,6 +43,7 @@ class CatalogDeclarativeDataset(Base): attributes: Optional[list[CatalogDeclarativeAttribute]] = None facts: Optional[list[CatalogDeclarativeFact]] = None aggregated_facts: Optional[list[CatalogDeclarativeAggregatedFact]] = attrs.field(factory=list) + precedence: Optional[int] = None data_source_table_id: Optional[CatalogDataSourceTableIdentifier] = None sql: Optional[CatalogDeclarativeDatasetSql] = None tags: Optional[list[str]] = None diff --git a/gooddata-sdk/gooddata_sdk/catalog/workspace/entity_model/content_objects/dataset.py b/gooddata-sdk/gooddata_sdk/catalog/workspace/entity_model/content_objects/dataset.py index 472985528..41754b96c 100644 --- a/gooddata-sdk/gooddata_sdk/catalog/workspace/entity_model/content_objects/dataset.py +++ b/gooddata-sdk/gooddata_sdk/catalog/workspace/entity_model/content_objects/dataset.py @@ -106,9 +106,7 @@ class CatalogAggregatedFact(AttrCatalogEntity): def client_class() -> Any: return JsonApiAggregatedFactOut - def as_computable(self) -> Metric: - return SimpleMetric(local_id=self.id, item=self.obj_id) - + # as_computable skipped because aggregated fact cannot be ever used in metric # TODO - dataset? @@ -131,20 +129,22 @@ def generate_attributes_from_api(self) -> list[CatalogAttribute]: repr=False, default=attr.Factory(lambda self: self.generate_attributes_from_api(), takes_self=True), ) - - def generate_facts_from_api(self) -> list[CatalogFact]: - related_fact_ids = [x.get("id") for x in safeget_list(self.json_api_relationships, ["facts", "data"])] - return [ - CatalogFact.from_api(sl) - for sl in self.json_api_side_loads - if sl["type"] == "fact" and sl["id"] in related_fact_ids - ] - facts: list[CatalogFact] = attr.field( repr=False, - default=attr.Factory(lambda self: self.generate_facts_from_api(), takes_self=True), + default=attr.Factory( + lambda self: self._relation_entity_from_side_loads(CatalogFact, ["facts", "data"]), takes_self=True + ), + ) + aggregated_facts: Optional[list[CatalogAggregatedFact]] = attr.field( + repr=False, + default=attr.Factory( + lambda self: self._relation_entity_from_side_loads(CatalogAggregatedFact, ["aggregatedFacts", "data"]), + takes_self=True, + ), + ) + precedence: Optional[int] = attr.field( + default=attr.Factory(lambda self: self.json_api_attributes.get("precedence"), takes_self=True) ) - grain: Optional[list] = attr.field( default=attr.Factory(lambda self: self.json_api_attributes.get("grain"), takes_self=True) ) diff --git a/gooddata-sdk/gooddata_sdk/catalog/workspace/model_container.py b/gooddata-sdk/gooddata_sdk/catalog/workspace/model_container.py index b5e29053b..289647e48 100644 --- a/gooddata-sdk/gooddata_sdk/catalog/workspace/model_container.py +++ b/gooddata-sdk/gooddata_sdk/catalog/workspace/model_container.py @@ -6,6 +6,7 @@ from gooddata_sdk.catalog.types import ValidObjects from gooddata_sdk.catalog.workspace.entity_model.content_objects.dataset import ( + CatalogAggregatedFact, CatalogAttribute, CatalogDataset, CatalogFact, @@ -46,6 +47,10 @@ def datasets(self) -> list[CatalogDataset]: def facts(self) -> list[CatalogFact]: return [f for d in self._datasets for f in d.facts] + @property + def aggregated_facts(self) -> list[CatalogAggregatedFact]: + return [f for d in self._datasets for f in (d.aggregated_facts if d.aggregated_facts else [])] + @property def attributes(self) -> list[CatalogAttribute]: return [a for d in self._datasets for a in d.attributes] diff --git a/gooddata-sdk/tests/catalog/fixtures/workspace_content/demo_catalog.yaml b/gooddata-sdk/tests/catalog/fixtures/workspace_content/demo_catalog.yaml index ec1b69206..0c33250a3 100644 --- a/gooddata-sdk/tests/catalog/fixtures/workspace_content/demo_catalog.yaml +++ b/gooddata-sdk/tests/catalog/fixtures/workspace_content/demo_catalog.yaml @@ -19,55 +19,35 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - '19974' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' Content-Type: - application/vnd.gooddata.api+json DATE: &id001 - PLACEHOLDER Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: data: @@ -121,31 +101,6 @@ interactions: origin: originType: NATIVE originId: demo - - id: type - type: attribute - attributes: - title: Type - description: Type - tags: - - Campaign channels - areRelationsValid: true - sourceColumn: type - sourceColumnDataType: STRING - relationships: - dataset: - data: - id: campaign_channels - type: dataset - labels: - data: - - id: type - type: label - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/type - meta: - origin: - originType: NATIVE - originId: demo - id: campaign_id type: attribute attributes: @@ -246,58 +201,122 @@ interactions: origin: originType: NATIVE originId: demo - - id: region + - id: date.day type: attribute attributes: - title: Region - description: Region + title: Date - Date + description: Date tags: - - Customers + - Date + granularity: DAY areRelationsValid: true - sourceColumn: region - sourceColumnDataType: STRING relationships: dataset: data: - id: customers + id: date type: dataset labels: data: - - id: region + - id: date.day type: label links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/region + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.day meta: origin: originType: NATIVE originId: demo - - id: state + - id: date.month type: attribute attributes: - title: State - description: State + title: Date - Month/Year + description: Month and Year (12/2020) tags: - - Customers + - Date + granularity: MONTH areRelationsValid: true - sourceColumn: state - sourceColumnDataType: STRING relationships: - defaultView: + dataset: data: - id: state - type: label + id: date + type: dataset + labels: + data: + - id: date.month + type: label + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.month + meta: + origin: + originType: NATIVE + originId: demo + - id: date.quarter + type: attribute + attributes: + title: Date - Quarter/Year + description: Quarter and Year (Q1/2020) + tags: + - Date + granularity: QUARTER + areRelationsValid: true + relationships: dataset: data: - id: customers + id: date type: dataset labels: data: - - id: state + - id: date.quarter type: label - - id: geo__state__location + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.quarter + meta: + origin: + originType: NATIVE + originId: demo + - id: date.week + type: attribute + attributes: + title: Date - Week/Year + description: Week and Year (W52/2020) + tags: + - Date + granularity: WEEK + areRelationsValid: true + relationships: + dataset: + data: + id: date + type: dataset + labels: + data: + - id: date.week type: label links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/state + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.week + meta: + origin: + originType: NATIVE + originId: demo + - id: date.year + type: attribute + attributes: + title: Date - Year + description: Year + tags: + - Date + granularity: YEAR + areRelationsValid: true + relationships: + dataset: + data: + id: date + type: dataset + labels: + data: + - id: date.year + type: label + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.year meta: origin: originType: NATIVE @@ -452,122 +471,83 @@ interactions: origin: originType: NATIVE originId: demo - - id: date.day + - id: region type: attribute attributes: - title: Date - Date - description: Date + title: Region + description: Region tags: - - Date - granularity: DAY + - Customers areRelationsValid: true + sourceColumn: region + sourceColumnDataType: STRING relationships: dataset: data: - id: date + id: customers type: dataset labels: data: - - id: date.day + - id: region type: label links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.day + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/region meta: origin: originType: NATIVE originId: demo - - id: date.week + - id: state type: attribute attributes: - title: Date - Week/Year - description: Week and Year (W52/2020) + title: State + description: State tags: - - Date - granularity: WEEK + - Customers areRelationsValid: true + sourceColumn: state + sourceColumnDataType: STRING relationships: - dataset: - data: - id: date - type: dataset - labels: + defaultView: data: - - id: date.week - type: label - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.week - meta: - origin: - originType: NATIVE - originId: demo - - id: date.month - type: attribute - attributes: - title: Date - Month/Year - description: Month and Year (12/2020) - tags: - - Date - granularity: MONTH - areRelationsValid: true - relationships: + id: state + type: label dataset: data: - id: date + id: customers type: dataset labels: data: - - id: date.month + - id: geo__state__location type: label - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.month - meta: - origin: - originType: NATIVE - originId: demo - - id: date.quarter - type: attribute - attributes: - title: Date - Quarter/Year - description: Quarter and Year (Q1/2020) - tags: - - Date - granularity: QUARTER - areRelationsValid: true - relationships: - dataset: - data: - id: date - type: dataset - labels: - data: - - id: date.quarter + - id: state type: label links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.quarter + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/state meta: origin: originType: NATIVE originId: demo - - id: date.year + - id: type type: attribute attributes: - title: Date - Year - description: Year + title: Type + description: Type tags: - - Date - granularity: YEAR + - Campaign channels areRelationsValid: true + sourceColumn: type + sourceColumnDataType: STRING relationships: dataset: data: - id: date + id: campaign_channels type: dataset labels: data: - - id: date.year + - id: type type: label links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.year + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/type meta: origin: originType: NATIVE @@ -610,18 +590,6 @@ interactions: - id: order_line_id type: attribute referenceProperties: - - identifier: - id: products - type: dataset - multivalue: false - sources: - - column: product_id - dataType: INT - target: - id: product_id - type: attribute - sourceColumns: null - sourceColumnDataTypes: null - identifier: id: date type: dataset @@ -658,14 +626,26 @@ interactions: type: attribute sourceColumns: null sourceColumnDataTypes: null - dataSourceTableId: demo-test-ds:order_lines - dataSourceTablePath: - - demo - - order_lines - workspaceDataFilterColumns: - - name: wdf__state - dataType: STRING - - name: wdf__region + - identifier: + id: products + type: dataset + multivalue: false + sources: + - column: product_id + dataType: INT + target: + id: product_id + type: attribute + sourceColumns: null + sourceColumnDataTypes: null + dataSourceTableId: demo-test-ds:order_lines + dataSourceTablePath: + - demo + - order_lines + workspaceDataFilterColumns: + - name: wdf__region + dataType: STRING + - name: wdf__state dataType: STRING workspaceDataFilterReferences: - filterId: @@ -1014,7 +994,7 @@ interactions: next: http://localhost:3000/api/v1/entities/workspaces/demo/attributes?include=labels%2Cdatasets&page=1&size=500 - request: method: GET - uri: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts&page=0&size=500 + uri: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts%2CaggregatedFacts&page=0&size=500 body: null headers: Accept: @@ -1030,141 +1010,150 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - - '12109' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' + - '13364' Content-Type: - application/vnd.gooddata.api+json DATE: *id001 Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: data: - - id: campaigns + - id: campaign_channels type: dataset attributes: - title: Campaigns - description: Campaigns + title: Campaign channels + description: Campaign channels tags: - - Campaigns + - Campaign channels grain: - - id: campaign_id + - id: campaign_channel_id type: attribute - dataSourceTableId: demo-test-ds:campaigns + referenceProperties: + - identifier: + id: campaigns + type: dataset + multivalue: false + sources: + - column: campaign_id + dataType: INT + target: + id: campaign_id + type: attribute + sourceColumns: null + sourceColumnDataTypes: null + dataSourceTableId: demo-test-ds:campaign_channels dataSourceTablePath: - demo - - campaigns + - campaign_channels areRelationsValid: true type: NORMAL relationships: attributes: data: - - id: campaign_id + - id: campaign_channel_id type: attribute - - id: campaign_name + - id: campaign_channels.category + type: attribute + - id: type type: attribute + facts: + data: + - id: budget + type: fact + - id: spend + type: fact links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/campaigns + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/campaign_channels meta: origin: originType: NATIVE originId: demo - - id: products + - id: campaign_channels_per_category type: dataset attributes: - title: Products - description: Products + title: Campaign channels per category + description: Campaign channels per categories tags: - - Products - grain: - - id: product_id - type: attribute - dataSourceTableId: demo-test-ds:products - dataSourceTablePath: - - demo - - products + - Campaign channels per category + referenceProperties: + - identifier: + id: campaign_channels + type: dataset + multivalue: false + sources: + - column: campaign_channel_id + dataType: STRING + target: + id: campaign_channel_id + type: attribute + sourceColumns: null + sourceColumnDataTypes: null + sql: + statement: SELECT category, SUM(budget) FROM campaign_channels GROUP + BY category + dataSourceId: demo-test-ds + precedence: 1 areRelationsValid: true type: NORMAL relationships: - attributes: + aggregatedFacts: data: - - id: product_id - type: attribute - - id: product_name - type: attribute - - id: products.category - type: attribute + - id: budget_agg + type: aggregatedFact links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/products + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/campaign_channels_per_category meta: origin: originType: NATIVE originId: demo - - id: date + - id: campaigns type: dataset attributes: - title: Date - description: '' + title: Campaigns + description: Campaigns tags: - - Date + - Campaigns + grain: + - id: campaign_id + type: attribute + dataSourceTableId: demo-test-ds:campaigns + dataSourceTablePath: + - demo + - campaigns areRelationsValid: true - type: DATE + type: NORMAL relationships: attributes: data: - - id: date.day - type: attribute - - id: date.week - type: attribute - - id: date.month - type: attribute - - id: date.quarter + - id: campaign_id type: attribute - - id: date.year + - id: campaign_name type: attribute links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/date + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/campaigns meta: origin: originType: NATIVE @@ -1202,6 +1191,34 @@ interactions: origin: originType: NATIVE originId: demo + - id: date + type: dataset + attributes: + title: Date + description: '' + tags: + - Date + areRelationsValid: true + type: DATE + relationships: + attributes: + data: + - id: date.day + type: attribute + - id: date.week + type: attribute + - id: date.month + type: attribute + - id: date.quarter + type: attribute + - id: date.year + type: attribute + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/date + meta: + origin: + originType: NATIVE + originId: demo - id: order_lines type: dataset attributes: @@ -1213,18 +1230,6 @@ interactions: - id: order_line_id type: attribute referenceProperties: - - identifier: - id: products - type: dataset - multivalue: false - sources: - - column: product_id - dataType: INT - target: - id: product_id - type: attribute - sourceColumns: null - sourceColumnDataTypes: null - identifier: id: date type: dataset @@ -1261,26 +1266,38 @@ interactions: type: attribute sourceColumns: null sourceColumnDataTypes: null + - identifier: + id: products + type: dataset + multivalue: false + sources: + - column: product_id + dataType: INT + target: + id: product_id + type: attribute + sourceColumns: null + sourceColumnDataTypes: null dataSourceTableId: demo-test-ds:order_lines dataSourceTablePath: - demo - order_lines areRelationsValid: true workspaceDataFilterColumns: - - name: wdf__state - dataType: STRING - name: wdf__region dataType: STRING + - name: wdf__state + dataType: STRING workspaceDataFilterReferences: - filterId: - id: wdf__region + id: wdf__state type: workspaceDataFilter - filterColumn: wdf__region + filterColumn: wdf__state filterColumnDataType: STRING - filterId: - id: wdf__state + id: wdf__region type: workspaceDataFilter - filterColumn: wdf__state + filterColumn: wdf__region filterColumnDataType: STRING type: NORMAL relationships: @@ -1304,68 +1321,38 @@ interactions: origin: originType: NATIVE originId: demo - - id: campaign_channels + - id: products type: dataset attributes: - title: Campaign channels - description: Campaign channels + title: Products + description: Products tags: - - Campaign channels + - Products grain: - - id: campaign_channel_id + - id: product_id type: attribute - referenceProperties: - - identifier: - id: campaigns - type: dataset - multivalue: false - sources: - - column: campaign_id - dataType: INT - target: - id: campaign_id - type: attribute - sourceColumns: null - sourceColumnDataTypes: null - dataSourceTableId: demo-test-ds:campaign_channels + dataSourceTableId: demo-test-ds:products dataSourceTablePath: - demo - - campaign_channels + - products areRelationsValid: true type: NORMAL relationships: attributes: data: - - id: campaign_channel_id + - id: product_id type: attribute - - id: campaign_channels.category + - id: product_name type: attribute - - id: type + - id: products.category type: attribute - facts: - data: - - id: budget - type: fact - - id: spend - type: fact links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/campaign_channels + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/products meta: origin: originType: NATIVE originId: demo included: - - id: campaign_name - type: attribute - attributes: - title: Campaign name - description: Campaign name - tags: - - Campaigns - sourceColumn: campaign_name - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_name - id: product_id type: attribute attributes: @@ -1377,17 +1364,6 @@ interactions: sourceColumnDataType: INT links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/product_id - - id: price - type: fact - attributes: - title: Price - description: Price - tags: - - Order lines - sourceColumn: price - sourceColumnDataType: NUMERIC - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/facts/price - id: budget type: fact attributes: @@ -1409,43 +1385,11 @@ interactions: granularity: YEAR links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.year - - id: date.day + - id: product_name type: attribute attributes: - title: Date - Date - description: Date - tags: - - Date - granularity: DAY - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.day - - id: region - type: attribute - attributes: - title: Region - description: Region - tags: - - Customers - sourceColumn: region - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/region - - id: campaign_channel_id - type: attribute - attributes: - title: Campaign channel id - description: Campaign channel id - tags: - - Campaign channels - sourceColumn: campaign_channel_id - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_channel_id - - id: product_name - type: attribute - attributes: - title: Product name - description: Product name + title: Product name + description: Product name tags: - Products sourceColumn: product_name @@ -1473,6 +1417,124 @@ interactions: sourceColumnDataType: STRING links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/products.category + - id: date.quarter + type: attribute + attributes: + title: Date - Quarter/Year + description: Quarter and Year (Q1/2020) + tags: + - Date + granularity: QUARTER + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.quarter + - id: campaign_channels.category + type: attribute + attributes: + title: Category + description: Category + tags: + - Campaign channels + sourceColumn: category + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_channels.category + - id: state + type: attribute + attributes: + title: State + description: State + tags: + - Customers + sourceColumn: state + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/state + - id: date.week + type: attribute + attributes: + title: Date - Week/Year + description: Week and Year (W52/2020) + tags: + - Date + granularity: WEEK + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.week + - id: order_id + type: attribute + attributes: + title: Order id + description: Order id + tags: + - Order lines + sourceColumn: order_id + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/order_id + - id: campaign_name + type: attribute + attributes: + title: Campaign name + description: Campaign name + tags: + - Campaigns + sourceColumn: campaign_name + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_name + - id: price + type: fact + attributes: + title: Price + description: Price + tags: + - Order lines + sourceColumn: price + sourceColumnDataType: NUMERIC + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/facts/price + - id: budget_agg + type: aggregatedFact + attributes: + description: Budget Agg + tags: + - Campaign channels per category + sourceColumn: budget + sourceColumnDataType: INT + operation: SUM + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/aggregatedFacts/budget_agg + - id: date.day + type: attribute + attributes: + title: Date - Date + description: Date + tags: + - Date + granularity: DAY + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.day + - id: region + type: attribute + attributes: + title: Region + description: Region + tags: + - Customers + sourceColumn: region + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/region + - id: campaign_channel_id + type: attribute + attributes: + title: Campaign channel id + description: Campaign channel id + tags: + - Campaign channels + sourceColumn: campaign_channel_id + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_channel_id - id: customer_id type: attribute attributes: @@ -1517,16 +1579,6 @@ interactions: sourceColumnDataType: STRING links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/type - - id: date.quarter - type: attribute - attributes: - title: Date - Quarter/Year - description: Quarter and Year (Q1/2020) - tags: - - Date - granularity: QUARTER - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.quarter - id: spend type: fact attributes: @@ -1538,38 +1590,6 @@ interactions: sourceColumnDataType: NUMERIC links: self: http://localhost:3000/api/v1/entities/workspaces/demo/facts/spend - - id: campaign_channels.category - type: attribute - attributes: - title: Category - description: Category - tags: - - Campaign channels - sourceColumn: category - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_channels.category - - id: state - type: attribute - attributes: - title: State - description: State - tags: - - Customers - sourceColumn: state - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/state - - id: date.week - type: attribute - attributes: - title: Date - Week/Year - description: Week and Year (W52/2020) - tags: - - Date - granularity: WEEK - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.week - id: order_status type: attribute attributes: @@ -1581,17 +1601,6 @@ interactions: sourceColumnDataType: STRING links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/order_status - - id: order_id - type: attribute - attributes: - title: Order id - description: Order id - tags: - - Order lines - sourceColumn: order_id - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/order_id - id: customer_name type: attribute attributes: @@ -1615,8 +1624,8 @@ interactions: links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/order_line_id links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts&page=0&size=500 - next: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts&page=1&size=500 + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts%2CaggregatedFacts&page=0&size=500 + next: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts%2CaggregatedFacts&page=1&size=500 - request: method: GET uri: http://localhost:3000/api/v1/entities/workspaces/demo/metrics?page=0&size=500 @@ -1635,428 +1644,408 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - '10543' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' Content-Type: - application/vnd.gooddata.api+json DATE: *id001 Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: data: - - id: percent_revenue_per_product + - id: amount_of_active_customers type: metric attributes: - title: '% Revenue per Product' + title: '# of Active Customers' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY ALL - {attribute/product_id}) + format: '#,##0' + maql: SELECT COUNT({attribute/customer_id},{attribute/order_line_id}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_per_product + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_active_customers meta: origin: originType: NATIVE originId: demo - - id: revenue + - id: amount_of_orders type: metric attributes: - title: Revenue - description: '' + title: '# of Orders' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/order_amount} WHERE NOT ({label/order_status} - IN ("Returned", "Canceled")) + format: '#,##0' + maql: SELECT COUNT({attribute/order_id}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_orders meta: origin: originType: NATIVE originId: demo - - id: revenue-clothing + - id: amount_of_top_customers type: metric attributes: - title: Revenue (Clothing) + title: '# of Top Customers' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/revenue} WHERE {label/products.category} IN - ("Clothing") + format: '#,##0' + maql: 'SELECT {metric/amount_of_active_customers} WHERE (SELECT + {metric/revenue} BY {attribute/customer_id}) > 10000 ' links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-clothing + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_top_customers meta: origin: originType: NATIVE originId: demo - - id: revenue-electronic + - id: amount_of_valid_orders type: metric attributes: - title: Revenue (Electronic) + title: '# of Valid Orders' + description: '' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/revenue} WHERE {label/products.category} IN - ( "Electronics") + format: '#,##0.00' + maql: SELECT {metric/amount_of_orders} WHERE NOT ({label/order_status} + IN ("Returned", "Canceled")) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-electronic + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_valid_orders meta: origin: originType: NATIVE originId: demo - - id: revenue-home + - id: campaign_spend type: metric attributes: - title: Revenue (Home) + title: Campaign Spend areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: format: $#,##0 - maql: SELECT {metric/revenue} WHERE {label/products.category} IN - ("Home") + maql: SELECT SUM({fact/spend}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-home + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/campaign_spend meta: origin: originType: NATIVE originId: demo - - id: revenue-outdoor + - id: order_amount type: metric attributes: - title: Revenue (Outdoor) + title: Order Amount areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: format: $#,##0 - maql: SELECT {metric/revenue} WHERE {label/products.category} IN - ("Outdoor") + maql: SELECT SUM({fact/price}*{fact/quantity}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-outdoor + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/order_amount meta: origin: originType: NATIVE originId: demo - - id: revenue_per_customer + - id: percent_revenue type: metric attributes: - title: Revenue per Customer + title: '% Revenue' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0.0 - maql: SELECT AVG(SELECT {metric/revenue} BY {attribute/customer_id}) + format: '#,##0.0%' + maql: SELECT {metric/revenue} / {metric/total_revenue} links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_per_customer + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue meta: origin: originType: NATIVE originId: demo - - id: revenue_per_dollar_spent + - id: percent_revenue_from_top_10_customers type: metric attributes: - title: Revenue per Dollar Spent + title: '% Revenue from Top 10 Customers' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0.0 - maql: SELECT {metric/revenue} / {metric/campaign_spend} + format: '#,##0.0%' + maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10}\ + \ BY {attribute/customer_id}) > 0)\n /\n {metric/revenue}" links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_per_dollar_spent + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_customers meta: origin: originType: NATIVE originId: demo - - id: revenue_top_10 + - id: percent_revenue_from_top_10_percent_customers type: metric attributes: - title: Revenue / Top 10 + title: '% Revenue from Top 10% Customers' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/revenue} WHERE TOP(10) OF ({metric/revenue}) + format: '#,##0.0%' + maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10_percent}\ + \ BY {attribute/customer_id}) > 0)\n /\n {metric/revenue}" links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_top_10 + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_percent_customers meta: origin: originType: NATIVE originId: demo - - id: revenue_top_10_percent + - id: percent_revenue_from_top_10_percent_products type: metric attributes: - title: Revenue / Top 10% + title: '% Revenue from Top 10% Products' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/revenue} WHERE TOP(10%) OF ({metric/revenue}) + format: '#,##0.0%' + maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10_percent}\ + \ BY {attribute/product_id}) > 0)\n /\n {metric/revenue}" links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_top_10_percent + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_percent_products meta: origin: originType: NATIVE originId: demo - - id: total_revenue + - id: percent_revenue_from_top_10_products type: metric attributes: - title: Total Revenue + title: '% Revenue from Top 10 Products' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/revenue} BY ALL OTHER + format: '#,##0.0%' + maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10}\ + \ BY {attribute/product_id}) > 0)\n /\n {metric/revenue}" links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/total_revenue + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_products meta: origin: originType: NATIVE originId: demo - - id: total_revenue-no_filters + - id: percent_revenue_in_category type: metric attributes: - title: Total Revenue (No Filters) + title: '% Revenue in Category' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/total_revenue} WITHOUT PARENT FILTER + format: '#,##0.0%' + maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY {attribute/products.category}, + ALL OTHER) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/total_revenue-no_filters + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_in_category meta: origin: originType: NATIVE originId: demo - - id: amount_of_active_customers + - id: percent_revenue_per_product type: metric attributes: - title: '# of Active Customers' + title: '% Revenue per Product' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0' - maql: SELECT COUNT({attribute/customer_id},{attribute/order_line_id}) + format: '#,##0.0%' + maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY ALL + {attribute/product_id}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_active_customers + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_per_product meta: origin: originType: NATIVE originId: demo - - id: amount_of_orders + - id: revenue type: metric attributes: - title: '# of Orders' + title: Revenue + description: '' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0' - maql: SELECT COUNT({attribute/order_id}) + format: $#,##0 + maql: SELECT {metric/order_amount} WHERE NOT ({label/order_status} + IN ("Returned", "Canceled")) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_orders + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue meta: origin: originType: NATIVE originId: demo - - id: amount_of_top_customers + - id: revenue-clothing type: metric attributes: - title: '# of Top Customers' + title: Revenue (Clothing) areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0' - maql: 'SELECT {metric/amount_of_active_customers} WHERE (SELECT - {metric/revenue} BY {attribute/customer_id}) > 10000 ' + format: $#,##0 + maql: SELECT {metric/revenue} WHERE {label/products.category} IN + ("Clothing") links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_top_customers + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-clothing meta: origin: originType: NATIVE originId: demo - - id: amount_of_valid_orders + - id: revenue-electronic type: metric attributes: - title: '# of Valid Orders' - description: '' + title: Revenue (Electronic) areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.00' - maql: SELECT {metric/amount_of_orders} WHERE NOT ({label/order_status} - IN ("Returned", "Canceled")) + format: $#,##0 + maql: SELECT {metric/revenue} WHERE {label/products.category} IN + ( "Electronics") links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_valid_orders + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-electronic meta: origin: originType: NATIVE originId: demo - - id: campaign_spend + - id: revenue-home type: metric attributes: - title: Campaign Spend + title: Revenue (Home) areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: format: $#,##0 - maql: SELECT SUM({fact/spend}) + maql: SELECT {metric/revenue} WHERE {label/products.category} IN + ("Home") links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/campaign_spend + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-home meta: origin: originType: NATIVE originId: demo - - id: order_amount + - id: revenue-outdoor type: metric attributes: - title: Order Amount + title: Revenue (Outdoor) areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: format: $#,##0 - maql: SELECT SUM({fact/price}*{fact/quantity}) + maql: SELECT {metric/revenue} WHERE {label/products.category} IN + ("Outdoor") links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/order_amount + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-outdoor meta: origin: originType: NATIVE originId: demo - - id: percent_revenue + - id: revenue_per_customer type: metric attributes: - title: '% Revenue' + title: Revenue per Customer areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: SELECT {metric/revenue} / {metric/total_revenue} + format: $#,##0.0 + maql: SELECT AVG(SELECT {metric/revenue} BY {attribute/customer_id}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_per_customer meta: origin: originType: NATIVE originId: demo - - id: percent_revenue_from_top_10_customers + - id: revenue_per_dollar_spent type: metric attributes: - title: '% Revenue from Top 10 Customers' + title: Revenue per Dollar Spent areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10}\ - \ BY {attribute/customer_id}) > 0)\n /\n {metric/revenue}" + format: $#,##0.0 + maql: SELECT {metric/revenue} / {metric/campaign_spend} links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_customers + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_per_dollar_spent meta: origin: originType: NATIVE originId: demo - - id: percent_revenue_from_top_10_percent_customers + - id: revenue_top_10 type: metric attributes: - title: '% Revenue from Top 10% Customers' + title: Revenue / Top 10 areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10_percent}\ - \ BY {attribute/customer_id}) > 0)\n /\n {metric/revenue}" + format: $#,##0 + maql: SELECT {metric/revenue} WHERE TOP(10) OF ({metric/revenue}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_percent_customers + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_top_10 meta: origin: originType: NATIVE originId: demo - - id: percent_revenue_from_top_10_percent_products + - id: revenue_top_10_percent type: metric attributes: - title: '% Revenue from Top 10% Products' + title: Revenue / Top 10% areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10_percent}\ - \ BY {attribute/product_id}) > 0)\n /\n {metric/revenue}" + format: $#,##0 + maql: SELECT {metric/revenue} WHERE TOP(10%) OF ({metric/revenue}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_percent_products + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_top_10_percent meta: origin: originType: NATIVE originId: demo - - id: percent_revenue_from_top_10_products + - id: total_revenue type: metric attributes: - title: '% Revenue from Top 10 Products' + title: Total Revenue areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10}\ - \ BY {attribute/product_id}) > 0)\n /\n {metric/revenue}" + format: $#,##0 + maql: SELECT {metric/revenue} BY ALL OTHER links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_products + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/total_revenue meta: origin: originType: NATIVE originId: demo - - id: percent_revenue_in_category + - id: total_revenue-no_filters type: metric attributes: - title: '% Revenue in Category' + title: Total Revenue (No Filters) areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY {attribute/products.category}, - ALL OTHER) + format: $#,##0 + maql: SELECT {metric/total_revenue} WITHOUT PARENT FILTER links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_in_category + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/total_revenue-no_filters meta: origin: originType: NATIVE diff --git a/gooddata-sdk/tests/catalog/fixtures/workspace_content/demo_catalog_availability.yaml b/gooddata-sdk/tests/catalog/fixtures/workspace_content/demo_catalog_availability.yaml index 6763d59d0..c6e820d06 100644 --- a/gooddata-sdk/tests/catalog/fixtures/workspace_content/demo_catalog_availability.yaml +++ b/gooddata-sdk/tests/catalog/fixtures/workspace_content/demo_catalog_availability.yaml @@ -19,55 +19,35 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - '19974' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' Content-Type: - application/vnd.gooddata.api+json DATE: &id001 - PLACEHOLDER Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: data: @@ -121,31 +101,6 @@ interactions: origin: originType: NATIVE originId: demo - - id: type - type: attribute - attributes: - title: Type - description: Type - tags: - - Campaign channels - areRelationsValid: true - sourceColumn: type - sourceColumnDataType: STRING - relationships: - dataset: - data: - id: campaign_channels - type: dataset - labels: - data: - - id: type - type: label - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/type - meta: - origin: - originType: NATIVE - originId: demo - id: campaign_id type: attribute attributes: @@ -246,58 +201,122 @@ interactions: origin: originType: NATIVE originId: demo - - id: region + - id: date.day type: attribute attributes: - title: Region - description: Region + title: Date - Date + description: Date tags: - - Customers + - Date + granularity: DAY areRelationsValid: true - sourceColumn: region - sourceColumnDataType: STRING relationships: dataset: data: - id: customers + id: date type: dataset labels: data: - - id: region + - id: date.day type: label links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/region + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.day meta: origin: originType: NATIVE originId: demo - - id: state + - id: date.month type: attribute attributes: - title: State - description: State + title: Date - Month/Year + description: Month and Year (12/2020) tags: - - Customers + - Date + granularity: MONTH areRelationsValid: true - sourceColumn: state - sourceColumnDataType: STRING relationships: - defaultView: + dataset: data: - id: state - type: label + id: date + type: dataset + labels: + data: + - id: date.month + type: label + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.month + meta: + origin: + originType: NATIVE + originId: demo + - id: date.quarter + type: attribute + attributes: + title: Date - Quarter/Year + description: Quarter and Year (Q1/2020) + tags: + - Date + granularity: QUARTER + areRelationsValid: true + relationships: dataset: data: - id: customers + id: date type: dataset labels: data: - - id: state + - id: date.quarter type: label - - id: geo__state__location + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.quarter + meta: + origin: + originType: NATIVE + originId: demo + - id: date.week + type: attribute + attributes: + title: Date - Week/Year + description: Week and Year (W52/2020) + tags: + - Date + granularity: WEEK + areRelationsValid: true + relationships: + dataset: + data: + id: date + type: dataset + labels: + data: + - id: date.week type: label links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/state + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.week + meta: + origin: + originType: NATIVE + originId: demo + - id: date.year + type: attribute + attributes: + title: Date - Year + description: Year + tags: + - Date + granularity: YEAR + areRelationsValid: true + relationships: + dataset: + data: + id: date + type: dataset + labels: + data: + - id: date.year + type: label + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.year meta: origin: originType: NATIVE @@ -452,122 +471,83 @@ interactions: origin: originType: NATIVE originId: demo - - id: date.day + - id: region type: attribute attributes: - title: Date - Date - description: Date + title: Region + description: Region tags: - - Date - granularity: DAY + - Customers areRelationsValid: true + sourceColumn: region + sourceColumnDataType: STRING relationships: dataset: data: - id: date + id: customers type: dataset labels: data: - - id: date.day + - id: region type: label links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.day + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/region meta: origin: originType: NATIVE originId: demo - - id: date.week + - id: state type: attribute attributes: - title: Date - Week/Year - description: Week and Year (W52/2020) + title: State + description: State tags: - - Date - granularity: WEEK + - Customers areRelationsValid: true + sourceColumn: state + sourceColumnDataType: STRING relationships: - dataset: - data: - id: date - type: dataset - labels: + defaultView: data: - - id: date.week - type: label - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.week - meta: - origin: - originType: NATIVE - originId: demo - - id: date.month - type: attribute - attributes: - title: Date - Month/Year - description: Month and Year (12/2020) - tags: - - Date - granularity: MONTH - areRelationsValid: true - relationships: + id: state + type: label dataset: data: - id: date + id: customers type: dataset labels: data: - - id: date.month + - id: geo__state__location type: label - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.month - meta: - origin: - originType: NATIVE - originId: demo - - id: date.quarter - type: attribute - attributes: - title: Date - Quarter/Year - description: Quarter and Year (Q1/2020) - tags: - - Date - granularity: QUARTER - areRelationsValid: true - relationships: - dataset: - data: - id: date - type: dataset - labels: - data: - - id: date.quarter + - id: state type: label links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.quarter + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/state meta: origin: originType: NATIVE originId: demo - - id: date.year + - id: type type: attribute attributes: - title: Date - Year - description: Year + title: Type + description: Type tags: - - Date - granularity: YEAR + - Campaign channels areRelationsValid: true + sourceColumn: type + sourceColumnDataType: STRING relationships: dataset: data: - id: date + id: campaign_channels type: dataset labels: data: - - id: date.year + - id: type type: label links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.year + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/type meta: origin: originType: NATIVE @@ -610,18 +590,6 @@ interactions: - id: order_line_id type: attribute referenceProperties: - - identifier: - id: products - type: dataset - multivalue: false - sources: - - column: product_id - dataType: INT - target: - id: product_id - type: attribute - sourceColumns: null - sourceColumnDataTypes: null - identifier: id: date type: dataset @@ -658,14 +626,26 @@ interactions: type: attribute sourceColumns: null sourceColumnDataTypes: null - dataSourceTableId: demo-test-ds:order_lines - dataSourceTablePath: - - demo - - order_lines - workspaceDataFilterColumns: - - name: wdf__state - dataType: STRING - - name: wdf__region + - identifier: + id: products + type: dataset + multivalue: false + sources: + - column: product_id + dataType: INT + target: + id: product_id + type: attribute + sourceColumns: null + sourceColumnDataTypes: null + dataSourceTableId: demo-test-ds:order_lines + dataSourceTablePath: + - demo + - order_lines + workspaceDataFilterColumns: + - name: wdf__region + dataType: STRING + - name: wdf__state dataType: STRING workspaceDataFilterReferences: - filterId: @@ -1014,7 +994,7 @@ interactions: next: http://localhost:3000/api/v1/entities/workspaces/demo/attributes?include=labels%2Cdatasets&page=1&size=500 - request: method: GET - uri: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts&page=0&size=500 + uri: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts%2CaggregatedFacts&page=0&size=500 body: null headers: Accept: @@ -1030,141 +1010,150 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - - '12109' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' + - '13364' Content-Type: - application/vnd.gooddata.api+json DATE: *id001 Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: data: - - id: campaigns + - id: campaign_channels type: dataset attributes: - title: Campaigns - description: Campaigns + title: Campaign channels + description: Campaign channels tags: - - Campaigns + - Campaign channels grain: - - id: campaign_id + - id: campaign_channel_id type: attribute - dataSourceTableId: demo-test-ds:campaigns + referenceProperties: + - identifier: + id: campaigns + type: dataset + multivalue: false + sources: + - column: campaign_id + dataType: INT + target: + id: campaign_id + type: attribute + sourceColumns: null + sourceColumnDataTypes: null + dataSourceTableId: demo-test-ds:campaign_channels dataSourceTablePath: - demo - - campaigns + - campaign_channels areRelationsValid: true type: NORMAL relationships: attributes: data: - - id: campaign_id + - id: campaign_channel_id type: attribute - - id: campaign_name + - id: campaign_channels.category + type: attribute + - id: type type: attribute + facts: + data: + - id: budget + type: fact + - id: spend + type: fact links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/campaigns + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/campaign_channels meta: origin: originType: NATIVE originId: demo - - id: products + - id: campaign_channels_per_category type: dataset attributes: - title: Products - description: Products + title: Campaign channels per category + description: Campaign channels per categories tags: - - Products - grain: - - id: product_id - type: attribute - dataSourceTableId: demo-test-ds:products - dataSourceTablePath: - - demo - - products + - Campaign channels per category + referenceProperties: + - identifier: + id: campaign_channels + type: dataset + multivalue: false + sources: + - column: campaign_channel_id + dataType: STRING + target: + id: campaign_channel_id + type: attribute + sourceColumns: null + sourceColumnDataTypes: null + sql: + statement: SELECT category, SUM(budget) FROM campaign_channels GROUP + BY category + dataSourceId: demo-test-ds + precedence: 1 areRelationsValid: true type: NORMAL relationships: - attributes: + aggregatedFacts: data: - - id: product_id - type: attribute - - id: product_name - type: attribute - - id: products.category - type: attribute + - id: budget_agg + type: aggregatedFact links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/products + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/campaign_channels_per_category meta: origin: originType: NATIVE originId: demo - - id: date + - id: campaigns type: dataset attributes: - title: Date - description: '' + title: Campaigns + description: Campaigns tags: - - Date + - Campaigns + grain: + - id: campaign_id + type: attribute + dataSourceTableId: demo-test-ds:campaigns + dataSourceTablePath: + - demo + - campaigns areRelationsValid: true - type: DATE + type: NORMAL relationships: attributes: data: - - id: date.day - type: attribute - - id: date.week - type: attribute - - id: date.month - type: attribute - - id: date.quarter + - id: campaign_id type: attribute - - id: date.year + - id: campaign_name type: attribute links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/date + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/campaigns meta: origin: originType: NATIVE @@ -1202,6 +1191,34 @@ interactions: origin: originType: NATIVE originId: demo + - id: date + type: dataset + attributes: + title: Date + description: '' + tags: + - Date + areRelationsValid: true + type: DATE + relationships: + attributes: + data: + - id: date.day + type: attribute + - id: date.week + type: attribute + - id: date.month + type: attribute + - id: date.quarter + type: attribute + - id: date.year + type: attribute + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/date + meta: + origin: + originType: NATIVE + originId: demo - id: order_lines type: dataset attributes: @@ -1213,18 +1230,6 @@ interactions: - id: order_line_id type: attribute referenceProperties: - - identifier: - id: products - type: dataset - multivalue: false - sources: - - column: product_id - dataType: INT - target: - id: product_id - type: attribute - sourceColumns: null - sourceColumnDataTypes: null - identifier: id: date type: dataset @@ -1261,26 +1266,38 @@ interactions: type: attribute sourceColumns: null sourceColumnDataTypes: null + - identifier: + id: products + type: dataset + multivalue: false + sources: + - column: product_id + dataType: INT + target: + id: product_id + type: attribute + sourceColumns: null + sourceColumnDataTypes: null dataSourceTableId: demo-test-ds:order_lines dataSourceTablePath: - demo - order_lines areRelationsValid: true workspaceDataFilterColumns: - - name: wdf__state - dataType: STRING - name: wdf__region dataType: STRING + - name: wdf__state + dataType: STRING workspaceDataFilterReferences: - filterId: - id: wdf__region + id: wdf__state type: workspaceDataFilter - filterColumn: wdf__region + filterColumn: wdf__state filterColumnDataType: STRING - filterId: - id: wdf__state + id: wdf__region type: workspaceDataFilter - filterColumn: wdf__state + filterColumn: wdf__region filterColumnDataType: STRING type: NORMAL relationships: @@ -1304,68 +1321,38 @@ interactions: origin: originType: NATIVE originId: demo - - id: campaign_channels + - id: products type: dataset attributes: - title: Campaign channels - description: Campaign channels + title: Products + description: Products tags: - - Campaign channels + - Products grain: - - id: campaign_channel_id + - id: product_id type: attribute - referenceProperties: - - identifier: - id: campaigns - type: dataset - multivalue: false - sources: - - column: campaign_id - dataType: INT - target: - id: campaign_id - type: attribute - sourceColumns: null - sourceColumnDataTypes: null - dataSourceTableId: demo-test-ds:campaign_channels + dataSourceTableId: demo-test-ds:products dataSourceTablePath: - demo - - campaign_channels + - products areRelationsValid: true type: NORMAL relationships: attributes: data: - - id: campaign_channel_id + - id: product_id type: attribute - - id: campaign_channels.category + - id: product_name type: attribute - - id: type + - id: products.category type: attribute - facts: - data: - - id: budget - type: fact - - id: spend - type: fact links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/campaign_channels + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/products meta: origin: originType: NATIVE originId: demo included: - - id: campaign_name - type: attribute - attributes: - title: Campaign name - description: Campaign name - tags: - - Campaigns - sourceColumn: campaign_name - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_name - id: product_id type: attribute attributes: @@ -1377,17 +1364,6 @@ interactions: sourceColumnDataType: INT links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/product_id - - id: price - type: fact - attributes: - title: Price - description: Price - tags: - - Order lines - sourceColumn: price - sourceColumnDataType: NUMERIC - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/facts/price - id: budget type: fact attributes: @@ -1409,43 +1385,11 @@ interactions: granularity: YEAR links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.year - - id: date.day + - id: product_name type: attribute attributes: - title: Date - Date - description: Date - tags: - - Date - granularity: DAY - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.day - - id: region - type: attribute - attributes: - title: Region - description: Region - tags: - - Customers - sourceColumn: region - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/region - - id: campaign_channel_id - type: attribute - attributes: - title: Campaign channel id - description: Campaign channel id - tags: - - Campaign channels - sourceColumn: campaign_channel_id - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_channel_id - - id: product_name - type: attribute - attributes: - title: Product name - description: Product name + title: Product name + description: Product name tags: - Products sourceColumn: product_name @@ -1473,6 +1417,124 @@ interactions: sourceColumnDataType: STRING links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/products.category + - id: date.quarter + type: attribute + attributes: + title: Date - Quarter/Year + description: Quarter and Year (Q1/2020) + tags: + - Date + granularity: QUARTER + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.quarter + - id: campaign_channels.category + type: attribute + attributes: + title: Category + description: Category + tags: + - Campaign channels + sourceColumn: category + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_channels.category + - id: state + type: attribute + attributes: + title: State + description: State + tags: + - Customers + sourceColumn: state + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/state + - id: date.week + type: attribute + attributes: + title: Date - Week/Year + description: Week and Year (W52/2020) + tags: + - Date + granularity: WEEK + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.week + - id: order_id + type: attribute + attributes: + title: Order id + description: Order id + tags: + - Order lines + sourceColumn: order_id + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/order_id + - id: campaign_name + type: attribute + attributes: + title: Campaign name + description: Campaign name + tags: + - Campaigns + sourceColumn: campaign_name + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_name + - id: price + type: fact + attributes: + title: Price + description: Price + tags: + - Order lines + sourceColumn: price + sourceColumnDataType: NUMERIC + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/facts/price + - id: budget_agg + type: aggregatedFact + attributes: + description: Budget Agg + tags: + - Campaign channels per category + sourceColumn: budget + sourceColumnDataType: INT + operation: SUM + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/aggregatedFacts/budget_agg + - id: date.day + type: attribute + attributes: + title: Date - Date + description: Date + tags: + - Date + granularity: DAY + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.day + - id: region + type: attribute + attributes: + title: Region + description: Region + tags: + - Customers + sourceColumn: region + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/region + - id: campaign_channel_id + type: attribute + attributes: + title: Campaign channel id + description: Campaign channel id + tags: + - Campaign channels + sourceColumn: campaign_channel_id + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_channel_id - id: customer_id type: attribute attributes: @@ -1517,16 +1579,6 @@ interactions: sourceColumnDataType: STRING links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/type - - id: date.quarter - type: attribute - attributes: - title: Date - Quarter/Year - description: Quarter and Year (Q1/2020) - tags: - - Date - granularity: QUARTER - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.quarter - id: spend type: fact attributes: @@ -1538,38 +1590,6 @@ interactions: sourceColumnDataType: NUMERIC links: self: http://localhost:3000/api/v1/entities/workspaces/demo/facts/spend - - id: campaign_channels.category - type: attribute - attributes: - title: Category - description: Category - tags: - - Campaign channels - sourceColumn: category - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_channels.category - - id: state - type: attribute - attributes: - title: State - description: State - tags: - - Customers - sourceColumn: state - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/state - - id: date.week - type: attribute - attributes: - title: Date - Week/Year - description: Week and Year (W52/2020) - tags: - - Date - granularity: WEEK - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.week - id: order_status type: attribute attributes: @@ -1581,17 +1601,6 @@ interactions: sourceColumnDataType: STRING links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/order_status - - id: order_id - type: attribute - attributes: - title: Order id - description: Order id - tags: - - Order lines - sourceColumn: order_id - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/order_id - id: customer_name type: attribute attributes: @@ -1615,8 +1624,8 @@ interactions: links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/order_line_id links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts&page=0&size=500 - next: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts&page=1&size=500 + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts%2CaggregatedFacts&page=0&size=500 + next: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts%2CaggregatedFacts&page=1&size=500 - request: method: GET uri: http://localhost:3000/api/v1/entities/workspaces/demo/metrics?page=0&size=500 @@ -1635,428 +1644,408 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - '10543' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' Content-Type: - application/vnd.gooddata.api+json DATE: *id001 Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: data: - - id: percent_revenue_per_product + - id: amount_of_active_customers type: metric attributes: - title: '% Revenue per Product' + title: '# of Active Customers' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY ALL - {attribute/product_id}) + format: '#,##0' + maql: SELECT COUNT({attribute/customer_id},{attribute/order_line_id}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_per_product + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_active_customers meta: origin: originType: NATIVE originId: demo - - id: revenue + - id: amount_of_orders type: metric attributes: - title: Revenue - description: '' + title: '# of Orders' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/order_amount} WHERE NOT ({label/order_status} - IN ("Returned", "Canceled")) + format: '#,##0' + maql: SELECT COUNT({attribute/order_id}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_orders meta: origin: originType: NATIVE originId: demo - - id: revenue-clothing + - id: amount_of_top_customers type: metric attributes: - title: Revenue (Clothing) + title: '# of Top Customers' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/revenue} WHERE {label/products.category} IN - ("Clothing") + format: '#,##0' + maql: 'SELECT {metric/amount_of_active_customers} WHERE (SELECT + {metric/revenue} BY {attribute/customer_id}) > 10000 ' links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-clothing + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_top_customers meta: origin: originType: NATIVE originId: demo - - id: revenue-electronic + - id: amount_of_valid_orders type: metric attributes: - title: Revenue (Electronic) + title: '# of Valid Orders' + description: '' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/revenue} WHERE {label/products.category} IN - ( "Electronics") + format: '#,##0.00' + maql: SELECT {metric/amount_of_orders} WHERE NOT ({label/order_status} + IN ("Returned", "Canceled")) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-electronic + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_valid_orders meta: origin: originType: NATIVE originId: demo - - id: revenue-home + - id: campaign_spend type: metric attributes: - title: Revenue (Home) + title: Campaign Spend areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: format: $#,##0 - maql: SELECT {metric/revenue} WHERE {label/products.category} IN - ("Home") + maql: SELECT SUM({fact/spend}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-home + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/campaign_spend meta: origin: originType: NATIVE originId: demo - - id: revenue-outdoor + - id: order_amount type: metric attributes: - title: Revenue (Outdoor) + title: Order Amount areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: format: $#,##0 - maql: SELECT {metric/revenue} WHERE {label/products.category} IN - ("Outdoor") + maql: SELECT SUM({fact/price}*{fact/quantity}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-outdoor + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/order_amount meta: origin: originType: NATIVE originId: demo - - id: revenue_per_customer + - id: percent_revenue type: metric attributes: - title: Revenue per Customer + title: '% Revenue' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0.0 - maql: SELECT AVG(SELECT {metric/revenue} BY {attribute/customer_id}) + format: '#,##0.0%' + maql: SELECT {metric/revenue} / {metric/total_revenue} links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_per_customer + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue meta: origin: originType: NATIVE originId: demo - - id: revenue_per_dollar_spent + - id: percent_revenue_from_top_10_customers type: metric attributes: - title: Revenue per Dollar Spent + title: '% Revenue from Top 10 Customers' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0.0 - maql: SELECT {metric/revenue} / {metric/campaign_spend} + format: '#,##0.0%' + maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10}\ + \ BY {attribute/customer_id}) > 0)\n /\n {metric/revenue}" links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_per_dollar_spent + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_customers meta: origin: originType: NATIVE originId: demo - - id: revenue_top_10 + - id: percent_revenue_from_top_10_percent_customers type: metric attributes: - title: Revenue / Top 10 + title: '% Revenue from Top 10% Customers' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/revenue} WHERE TOP(10) OF ({metric/revenue}) + format: '#,##0.0%' + maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10_percent}\ + \ BY {attribute/customer_id}) > 0)\n /\n {metric/revenue}" links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_top_10 + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_percent_customers meta: origin: originType: NATIVE originId: demo - - id: revenue_top_10_percent + - id: percent_revenue_from_top_10_percent_products type: metric attributes: - title: Revenue / Top 10% + title: '% Revenue from Top 10% Products' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/revenue} WHERE TOP(10%) OF ({metric/revenue}) + format: '#,##0.0%' + maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10_percent}\ + \ BY {attribute/product_id}) > 0)\n /\n {metric/revenue}" links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_top_10_percent + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_percent_products meta: origin: originType: NATIVE originId: demo - - id: total_revenue + - id: percent_revenue_from_top_10_products type: metric attributes: - title: Total Revenue + title: '% Revenue from Top 10 Products' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/revenue} BY ALL OTHER + format: '#,##0.0%' + maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10}\ + \ BY {attribute/product_id}) > 0)\n /\n {metric/revenue}" links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/total_revenue + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_products meta: origin: originType: NATIVE originId: demo - - id: total_revenue-no_filters + - id: percent_revenue_in_category type: metric attributes: - title: Total Revenue (No Filters) + title: '% Revenue in Category' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/total_revenue} WITHOUT PARENT FILTER + format: '#,##0.0%' + maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY {attribute/products.category}, + ALL OTHER) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/total_revenue-no_filters + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_in_category meta: origin: originType: NATIVE originId: demo - - id: amount_of_active_customers + - id: percent_revenue_per_product type: metric attributes: - title: '# of Active Customers' + title: '% Revenue per Product' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0' - maql: SELECT COUNT({attribute/customer_id},{attribute/order_line_id}) + format: '#,##0.0%' + maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY ALL + {attribute/product_id}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_active_customers + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_per_product meta: origin: originType: NATIVE originId: demo - - id: amount_of_orders + - id: revenue type: metric attributes: - title: '# of Orders' + title: Revenue + description: '' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0' - maql: SELECT COUNT({attribute/order_id}) + format: $#,##0 + maql: SELECT {metric/order_amount} WHERE NOT ({label/order_status} + IN ("Returned", "Canceled")) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_orders + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue meta: origin: originType: NATIVE originId: demo - - id: amount_of_top_customers + - id: revenue-clothing type: metric attributes: - title: '# of Top Customers' + title: Revenue (Clothing) areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0' - maql: 'SELECT {metric/amount_of_active_customers} WHERE (SELECT - {metric/revenue} BY {attribute/customer_id}) > 10000 ' + format: $#,##0 + maql: SELECT {metric/revenue} WHERE {label/products.category} IN + ("Clothing") links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_top_customers + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-clothing meta: origin: originType: NATIVE originId: demo - - id: amount_of_valid_orders + - id: revenue-electronic type: metric attributes: - title: '# of Valid Orders' - description: '' + title: Revenue (Electronic) areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.00' - maql: SELECT {metric/amount_of_orders} WHERE NOT ({label/order_status} - IN ("Returned", "Canceled")) + format: $#,##0 + maql: SELECT {metric/revenue} WHERE {label/products.category} IN + ( "Electronics") links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_valid_orders + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-electronic meta: origin: originType: NATIVE originId: demo - - id: campaign_spend + - id: revenue-home type: metric attributes: - title: Campaign Spend + title: Revenue (Home) areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: format: $#,##0 - maql: SELECT SUM({fact/spend}) + maql: SELECT {metric/revenue} WHERE {label/products.category} IN + ("Home") links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/campaign_spend + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-home meta: origin: originType: NATIVE originId: demo - - id: order_amount + - id: revenue-outdoor type: metric attributes: - title: Order Amount + title: Revenue (Outdoor) areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: format: $#,##0 - maql: SELECT SUM({fact/price}*{fact/quantity}) + maql: SELECT {metric/revenue} WHERE {label/products.category} IN + ("Outdoor") links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/order_amount + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-outdoor meta: origin: originType: NATIVE originId: demo - - id: percent_revenue + - id: revenue_per_customer type: metric attributes: - title: '% Revenue' + title: Revenue per Customer areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: SELECT {metric/revenue} / {metric/total_revenue} + format: $#,##0.0 + maql: SELECT AVG(SELECT {metric/revenue} BY {attribute/customer_id}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_per_customer meta: origin: originType: NATIVE originId: demo - - id: percent_revenue_from_top_10_customers + - id: revenue_per_dollar_spent type: metric attributes: - title: '% Revenue from Top 10 Customers' + title: Revenue per Dollar Spent areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10}\ - \ BY {attribute/customer_id}) > 0)\n /\n {metric/revenue}" + format: $#,##0.0 + maql: SELECT {metric/revenue} / {metric/campaign_spend} links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_customers + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_per_dollar_spent meta: origin: originType: NATIVE originId: demo - - id: percent_revenue_from_top_10_percent_customers + - id: revenue_top_10 type: metric attributes: - title: '% Revenue from Top 10% Customers' + title: Revenue / Top 10 areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10_percent}\ - \ BY {attribute/customer_id}) > 0)\n /\n {metric/revenue}" + format: $#,##0 + maql: SELECT {metric/revenue} WHERE TOP(10) OF ({metric/revenue}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_percent_customers + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_top_10 meta: origin: originType: NATIVE originId: demo - - id: percent_revenue_from_top_10_percent_products + - id: revenue_top_10_percent type: metric attributes: - title: '% Revenue from Top 10% Products' + title: Revenue / Top 10% areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10_percent}\ - \ BY {attribute/product_id}) > 0)\n /\n {metric/revenue}" + format: $#,##0 + maql: SELECT {metric/revenue} WHERE TOP(10%) OF ({metric/revenue}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_percent_products + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_top_10_percent meta: origin: originType: NATIVE originId: demo - - id: percent_revenue_from_top_10_products + - id: total_revenue type: metric attributes: - title: '% Revenue from Top 10 Products' + title: Total Revenue areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10}\ - \ BY {attribute/product_id}) > 0)\n /\n {metric/revenue}" + format: $#,##0 + maql: SELECT {metric/revenue} BY ALL OTHER links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_products + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/total_revenue meta: origin: originType: NATIVE originId: demo - - id: percent_revenue_in_category + - id: total_revenue-no_filters type: metric attributes: - title: '% Revenue in Category' + title: Total Revenue (No Filters) areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY {attribute/products.category}, - ALL OTHER) + format: $#,##0 + maql: SELECT {metric/total_revenue} WITHOUT PARENT FILTER links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_in_category + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/total_revenue-no_filters meta: origin: originType: NATIVE @@ -2101,56 +2090,34 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' + Content-Length: + - '1502' Content-Type: - application/json DATE: *id001 Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx - Transfer-Encoding: - - chunked + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' - content-length: - - '1502' + X-Xss-Protection: + - 1; mode=block body: string: items: diff --git a/gooddata-sdk/tests/catalog/fixtures/workspace_content/demo_catalog_list_aggregated_facts.yaml b/gooddata-sdk/tests/catalog/fixtures/workspace_content/demo_catalog_list_aggregated_facts.yaml index e7404bd01..9347f5897 100644 --- a/gooddata-sdk/tests/catalog/fixtures/workspace_content/demo_catalog_list_aggregated_facts.yaml +++ b/gooddata-sdk/tests/catalog/fixtures/workspace_content/demo_catalog_list_aggregated_facts.yaml @@ -19,58 +19,54 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - - '211' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' + - '594' Content-Type: - application/vnd.gooddata.api+json DATE: &id001 - PLACEHOLDER Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: - data: [] + data: + - id: budget_agg + type: aggregatedFact + attributes: + description: Budget Agg + tags: + - Campaign channels per category + sourceColumn: budget + sourceColumnDataType: INT + areRelationsValid: true + operation: SUM + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/aggregatedFacts/budget_agg + meta: + origin: + originType: NATIVE + originId: demo links: self: http://localhost:3000/api/v1/entities/workspaces/demo/aggregatedFacts?page=0&size=500 next: http://localhost:3000/api/v1/entities/workspaces/demo/aggregatedFacts?page=1&size=500 diff --git a/gooddata-sdk/tests/catalog/fixtures/workspace_content/demo_load_ldm_and_modify_tables_columns_case.yaml b/gooddata-sdk/tests/catalog/fixtures/workspace_content/demo_load_ldm_and_modify_tables_columns_case.yaml index 8d48b019a..110802c79 100644 --- a/gooddata-sdk/tests/catalog/fixtures/workspace_content/demo_load_ldm_and_modify_tables_columns_case.yaml +++ b/gooddata-sdk/tests/catalog/fixtures/workspace_content/demo_load_ldm_and_modify_tables_columns_case.yaml @@ -19,57 +19,35 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' + Content-Length: + - '7019' Content-Type: - application/json DATE: &id001 - PLACEHOLDER Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx - Transfer-Encoding: - - chunked + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' - content-length: - - '6211' + X-Xss-Protection: + - 1; mode=block body: string: ldm: @@ -141,6 +119,42 @@ interactions: tags: - Campaign channels title: Campaign channels + - aggregatedFacts: + - description: Budget Agg + id: budget_agg + sourceColumn: budget + sourceColumnDataType: INT + sourceFactReference: + operation: SUM + reference: + id: budget + type: fact + tags: + - Campaign channels per category + attributes: [] + description: Campaign channels per categories + facts: [] + grain: [] + id: campaign_channels_per_category + precedence: 1 + references: + - identifier: + id: campaign_channels + type: dataset + multivalue: false + sources: + - column: campaign_channel_id + dataType: STRING + target: + id: campaign_channel_id + type: attribute + sql: + dataSourceId: demo-test-ds + statement: SELECT category, SUM(budget) FROM campaign_channels GROUP + BY category + tags: + - Campaign channels per category + title: Campaign channels per category - aggregatedFacts: [] attributes: - description: Campaign id diff --git a/gooddata-sdk/tests/catalog/fixtures/workspace_content/explicit_workspace_data_filter.yaml b/gooddata-sdk/tests/catalog/fixtures/workspace_content/explicit_workspace_data_filter.yaml index bdd590005..883853a09 100644 --- a/gooddata-sdk/tests/catalog/fixtures/workspace_content/explicit_workspace_data_filter.yaml +++ b/gooddata-sdk/tests/catalog/fixtures/workspace_content/explicit_workspace_data_filter.yaml @@ -19,57 +19,35 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' + Content-Length: + - '7019' Content-Type: - application/json DATE: &id001 - PLACEHOLDER Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx - Transfer-Encoding: - - chunked + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' - content-length: - - '6211' + X-Xss-Protection: + - 1; mode=block body: string: ldm: @@ -141,6 +119,42 @@ interactions: tags: - Campaign channels title: Campaign channels + - aggregatedFacts: + - description: Budget Agg + id: budget_agg + sourceColumn: budget + sourceColumnDataType: INT + sourceFactReference: + operation: SUM + reference: + id: budget + type: fact + tags: + - Campaign channels per category + attributes: [] + description: Campaign channels per categories + facts: [] + grain: [] + id: campaign_channels_per_category + precedence: 1 + references: + - identifier: + id: campaign_channels + type: dataset + multivalue: false + sources: + - column: campaign_channel_id + dataType: STRING + target: + id: campaign_channel_id + type: attribute + sql: + dataSourceId: demo-test-ds + statement: SELECT category, SUM(budget) FROM campaign_channels GROUP + BY category + tags: + - Campaign channels per category + title: Campaign channels per category - aggregatedFacts: [] attributes: - description: Campaign id @@ -474,6 +488,42 @@ interactions: - campaign_channels tags: - Campaign channels + - grain: [] + id: campaign_channels_per_category + references: + - identifier: + id: campaign_channels + type: dataset + multivalue: false + sources: + - column: campaign_channel_id + target: + id: campaign_channel_id + type: attribute + dataType: STRING + title: Campaign channels per category + description: Campaign channels per categories + attributes: [] + facts: [] + aggregatedFacts: + - id: budget_agg + sourceColumn: budget + sourceFactReference: + operation: SUM + reference: + id: budget + type: fact + sourceColumnDataType: INT + description: Budget Agg + tags: + - Campaign channels per category + precedence: 1 + sql: + dataSourceId: demo-test-ds + statement: SELECT category, SUM(budget) FROM campaign_channels GROUP + BY category + tags: + - Campaign channels per category - grain: - id: campaign_id type: attribute @@ -754,50 +804,30 @@ interactions: code: 204 message: No Content headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' DATE: *id001 Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: '' - request: @@ -818,56 +848,34 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' + Content-Length: + - '7177' Content-Type: - application/json DATE: *id001 Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx - Transfer-Encoding: - - chunked + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' - content-length: - - '6369' + X-Xss-Protection: + - 1; mode=block body: string: ldm: @@ -939,6 +947,42 @@ interactions: tags: - Campaign channels title: Campaign channels + - aggregatedFacts: + - description: Budget Agg + id: budget_agg + sourceColumn: budget + sourceColumnDataType: INT + sourceFactReference: + operation: SUM + reference: + id: budget + type: fact + tags: + - Campaign channels per category + attributes: [] + description: Campaign channels per categories + facts: [] + grain: [] + id: campaign_channels_per_category + precedence: 1 + references: + - identifier: + id: campaign_channels + type: dataset + multivalue: false + sources: + - column: campaign_channel_id + dataType: STRING + target: + id: campaign_channel_id + type: attribute + sql: + dataSourceId: demo-test-ds + statement: SELECT category, SUM(budget) FROM campaign_channels GROUP + BY category + tags: + - Campaign channels per category + title: Campaign channels per category - aggregatedFacts: [] attributes: - description: Campaign id @@ -1223,54 +1267,34 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - '20132' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' Content-Type: - application/vnd.gooddata.api+json DATE: *id001 Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: data: @@ -1324,31 +1348,6 @@ interactions: origin: originType: NATIVE originId: demo - - id: type - type: attribute - attributes: - title: Type - description: Type - tags: - - Campaign channels - areRelationsValid: true - sourceColumn: type - sourceColumnDataType: STRING - relationships: - dataset: - data: - id: campaign_channels - type: dataset - labels: - data: - - id: type - type: label - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/type - meta: - origin: - originType: NATIVE - originId: demo - id: campaign_id type: attribute attributes: @@ -1449,58 +1448,122 @@ interactions: origin: originType: NATIVE originId: demo - - id: region + - id: date.day type: attribute attributes: - title: Region - description: Region + title: Date - Date + description: Date tags: - - Customers + - Date + granularity: DAY areRelationsValid: true - sourceColumn: region - sourceColumnDataType: STRING relationships: dataset: data: - id: customers + id: date type: dataset labels: data: - - id: region + - id: date.day type: label links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/region + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.day meta: origin: originType: NATIVE originId: demo - - id: state + - id: date.month type: attribute attributes: - title: State - description: State + title: Date - Month/Year + description: Month and Year (12/2020) tags: - - Customers + - Date + granularity: MONTH areRelationsValid: true - sourceColumn: state - sourceColumnDataType: STRING relationships: - defaultView: + dataset: data: - id: state - type: label + id: date + type: dataset + labels: + data: + - id: date.month + type: label + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.month + meta: + origin: + originType: NATIVE + originId: demo + - id: date.quarter + type: attribute + attributes: + title: Date - Quarter/Year + description: Quarter and Year (Q1/2020) + tags: + - Date + granularity: QUARTER + areRelationsValid: true + relationships: dataset: data: - id: customers + id: date type: dataset labels: data: - - id: state + - id: date.quarter type: label - - id: geo__state__location + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.quarter + meta: + origin: + originType: NATIVE + originId: demo + - id: date.week + type: attribute + attributes: + title: Date - Week/Year + description: Week and Year (W52/2020) + tags: + - Date + granularity: WEEK + areRelationsValid: true + relationships: + dataset: + data: + id: date + type: dataset + labels: + data: + - id: date.week type: label links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/state + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.week + meta: + origin: + originType: NATIVE + originId: demo + - id: date.year + type: attribute + attributes: + title: Date - Year + description: Year + tags: + - Date + granularity: YEAR + areRelationsValid: true + relationships: + dataset: + data: + id: date + type: dataset + labels: + data: + - id: date.year + type: label + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.year meta: origin: originType: NATIVE @@ -1655,132 +1718,93 @@ interactions: origin: originType: NATIVE originId: demo - - id: date.day + - id: region type: attribute attributes: - title: Date - Date - description: Date + title: Region + description: Region tags: - - Date - granularity: DAY + - Customers areRelationsValid: true + sourceColumn: region + sourceColumnDataType: STRING relationships: dataset: data: - id: date + id: customers type: dataset labels: data: - - id: date.day + - id: region type: label links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.day + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/region meta: origin: originType: NATIVE originId: demo - - id: date.week + - id: state type: attribute attributes: - title: Date - Week/Year - description: Week and Year (W52/2020) + title: State + description: State tags: - - Date - granularity: WEEK + - Customers areRelationsValid: true + sourceColumn: state + sourceColumnDataType: STRING relationships: + defaultView: + data: + id: state + type: label dataset: data: - id: date + id: customers type: dataset labels: data: - - id: date.week + - id: geo__state__location + type: label + - id: state type: label links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.week + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/state meta: origin: originType: NATIVE originId: demo - - id: date.month + - id: type type: attribute attributes: - title: Date - Month/Year - description: Month and Year (12/2020) + title: Type + description: Type tags: - - Date - granularity: MONTH + - Campaign channels areRelationsValid: true + sourceColumn: type + sourceColumnDataType: STRING relationships: dataset: data: - id: date + id: campaign_channels type: dataset labels: data: - - id: date.month + - id: type type: label links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.month + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/type meta: origin: originType: NATIVE originId: demo - - id: date.quarter - type: attribute + included: + - id: product_name + type: label attributes: - title: Date - Quarter/Year - description: Quarter and Year (Q1/2020) - tags: - - Date - granularity: QUARTER - areRelationsValid: true - relationships: - dataset: - data: - id: date - type: dataset - labels: - data: - - id: date.quarter - type: label - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.quarter - meta: - origin: - originType: NATIVE - originId: demo - - id: date.year - type: attribute - attributes: - title: Date - Year - description: Year - tags: - - Date - granularity: YEAR - areRelationsValid: true - relationships: - dataset: - data: - id: date - type: dataset - labels: - data: - - id: date.year - type: label - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.year - meta: - origin: - originType: NATIVE - originId: demo - included: - - id: product_name - type: label - attributes: - title: Product name - description: Product name + title: Product name + description: Product name tags: - Products primary: true @@ -1813,18 +1837,6 @@ interactions: - id: order_line_id type: attribute referenceProperties: - - identifier: - id: products - type: dataset - multivalue: false - sources: - - column: product_id - dataType: INT - target: - id: product_id - type: attribute - sourceColumns: null - sourceColumnDataTypes: null - identifier: id: date type: dataset @@ -1861,15 +1873,27 @@ interactions: type: attribute sourceColumns: null sourceColumnDataTypes: null + - identifier: + id: products + type: dataset + multivalue: false + sources: + - column: product_id + dataType: INT + target: + id: product_id + type: attribute + sourceColumns: null + sourceColumnDataTypes: null dataSourceTableId: demo-test-ds:order_lines dataSourceTablePath: - demo - order_lines workspaceDataFilterColumns: - - name: wdf__state - dataType: STRING - name: wdf__region dataType: STRING + - name: wdf__state + dataType: STRING workspaceDataFilterReferences: - filterId: id: wdf__state @@ -2223,7 +2247,7 @@ interactions: next: http://localhost:3000/api/v1/entities/workspaces/demo/attributes?include=labels%2Cdatasets&page=1&size=500 - request: method: GET - uri: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts&page=0&size=500 + uri: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts%2CaggregatedFacts&page=0&size=500 body: null headers: Accept: @@ -2239,141 +2263,150 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - - '12267' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' + - '13522' Content-Type: - application/vnd.gooddata.api+json DATE: *id001 Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: data: - - id: campaigns + - id: campaign_channels type: dataset attributes: - title: Campaigns - description: Campaigns + title: Campaign channels + description: Campaign channels tags: - - Campaigns + - Campaign channels grain: - - id: campaign_id + - id: campaign_channel_id type: attribute - dataSourceTableId: demo-test-ds:campaigns + referenceProperties: + - identifier: + id: campaigns + type: dataset + multivalue: false + sources: + - column: campaign_id + dataType: INT + target: + id: campaign_id + type: attribute + sourceColumns: null + sourceColumnDataTypes: null + dataSourceTableId: demo-test-ds:campaign_channels dataSourceTablePath: - demo - - campaigns + - campaign_channels areRelationsValid: true type: NORMAL relationships: attributes: data: - - id: campaign_id + - id: campaign_channel_id type: attribute - - id: campaign_name + - id: campaign_channels.category + type: attribute + - id: type type: attribute + facts: + data: + - id: budget + type: fact + - id: spend + type: fact links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/campaigns + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/campaign_channels meta: origin: originType: NATIVE originId: demo - - id: products + - id: campaign_channels_per_category type: dataset attributes: - title: Products - description: Products + title: Campaign channels per category + description: Campaign channels per categories tags: - - Products - grain: - - id: product_id - type: attribute - dataSourceTableId: demo-test-ds:products - dataSourceTablePath: - - demo - - products + - Campaign channels per category + referenceProperties: + - identifier: + id: campaign_channels + type: dataset + multivalue: false + sources: + - column: campaign_channel_id + dataType: STRING + target: + id: campaign_channel_id + type: attribute + sourceColumns: null + sourceColumnDataTypes: null + sql: + statement: SELECT category, SUM(budget) FROM campaign_channels GROUP + BY category + dataSourceId: demo-test-ds + precedence: 1 areRelationsValid: true type: NORMAL relationships: - attributes: + aggregatedFacts: data: - - id: product_id - type: attribute - - id: product_name - type: attribute - - id: products.category - type: attribute + - id: budget_agg + type: aggregatedFact links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/products + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/campaign_channels_per_category meta: origin: originType: NATIVE originId: demo - - id: date + - id: campaigns type: dataset attributes: - title: Date - description: '' + title: Campaigns + description: Campaigns tags: - - Date + - Campaigns + grain: + - id: campaign_id + type: attribute + dataSourceTableId: demo-test-ds:campaigns + dataSourceTablePath: + - demo + - campaigns areRelationsValid: true - type: DATE + type: NORMAL relationships: attributes: data: - - id: date.day - type: attribute - - id: date.week - type: attribute - - id: date.month - type: attribute - - id: date.quarter + - id: campaign_id type: attribute - - id: date.year + - id: campaign_name type: attribute links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/date + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/campaigns meta: origin: originType: NATIVE @@ -2417,6 +2450,34 @@ interactions: origin: originType: NATIVE originId: demo + - id: date + type: dataset + attributes: + title: Date + description: '' + tags: + - Date + areRelationsValid: true + type: DATE + relationships: + attributes: + data: + - id: date.day + type: attribute + - id: date.week + type: attribute + - id: date.month + type: attribute + - id: date.quarter + type: attribute + - id: date.year + type: attribute + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/date + meta: + origin: + originType: NATIVE + originId: demo - id: order_lines type: dataset attributes: @@ -2428,18 +2489,6 @@ interactions: - id: order_line_id type: attribute referenceProperties: - - identifier: - id: products - type: dataset - multivalue: false - sources: - - column: product_id - dataType: INT - target: - id: product_id - type: attribute - sourceColumns: null - sourceColumnDataTypes: null - identifier: id: date type: dataset @@ -2476,26 +2525,38 @@ interactions: type: attribute sourceColumns: null sourceColumnDataTypes: null + - identifier: + id: products + type: dataset + multivalue: false + sources: + - column: product_id + dataType: INT + target: + id: product_id + type: attribute + sourceColumns: null + sourceColumnDataTypes: null dataSourceTableId: demo-test-ds:order_lines dataSourceTablePath: - demo - order_lines areRelationsValid: true workspaceDataFilterColumns: - - name: wdf__state - dataType: STRING - name: wdf__region dataType: STRING + - name: wdf__state + dataType: STRING workspaceDataFilterReferences: - filterId: - id: wdf__state + id: wdf__region type: workspaceDataFilter - filterColumn: wdf__state + filterColumn: wdf__region filterColumnDataType: STRING - filterId: - id: wdf__region + id: wdf__state type: workspaceDataFilter - filterColumn: wdf__region + filterColumn: wdf__state filterColumnDataType: STRING type: NORMAL relationships: @@ -2519,68 +2580,38 @@ interactions: origin: originType: NATIVE originId: demo - - id: campaign_channels + - id: products type: dataset attributes: - title: Campaign channels - description: Campaign channels + title: Products + description: Products tags: - - Campaign channels + - Products grain: - - id: campaign_channel_id + - id: product_id type: attribute - referenceProperties: - - identifier: - id: campaigns - type: dataset - multivalue: false - sources: - - column: campaign_id - dataType: INT - target: - id: campaign_id - type: attribute - sourceColumns: null - sourceColumnDataTypes: null - dataSourceTableId: demo-test-ds:campaign_channels + dataSourceTableId: demo-test-ds:products dataSourceTablePath: - demo - - campaign_channels + - products areRelationsValid: true type: NORMAL relationships: attributes: data: - - id: campaign_channel_id + - id: product_id type: attribute - - id: campaign_channels.category + - id: product_name type: attribute - - id: type + - id: products.category type: attribute - facts: - data: - - id: budget - type: fact - - id: spend - type: fact links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/campaign_channels + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets/products meta: origin: originType: NATIVE originId: demo included: - - id: campaign_name - type: attribute - attributes: - title: Campaign name - description: Campaign name - tags: - - Campaigns - sourceColumn: campaign_name - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_name - id: product_id type: attribute attributes: @@ -2592,17 +2623,6 @@ interactions: sourceColumnDataType: INT links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/product_id - - id: price - type: fact - attributes: - title: Price - description: Price - tags: - - Order lines - sourceColumn: price - sourceColumnDataType: NUMERIC - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/facts/price - id: budget type: fact attributes: @@ -2624,38 +2644,6 @@ interactions: granularity: YEAR links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.year - - id: date.day - type: attribute - attributes: - title: Date - Date - description: Date - tags: - - Date - granularity: DAY - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.day - - id: region - type: attribute - attributes: - title: Region - description: Region - tags: - - Customers - sourceColumn: region - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/region - - id: campaign_channel_id - type: attribute - attributes: - title: Campaign channel id - description: Campaign channel id - tags: - - Campaign channels - sourceColumn: campaign_channel_id - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_channel_id - id: product_name type: attribute attributes: @@ -2688,6 +2676,124 @@ interactions: sourceColumnDataType: STRING links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/products.category + - id: date.quarter + type: attribute + attributes: + title: Date - Quarter/Year + description: Quarter and Year (Q1/2020) + tags: + - Date + granularity: QUARTER + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.quarter + - id: campaign_channels.category + type: attribute + attributes: + title: Category + description: Category + tags: + - Campaign channels + sourceColumn: category + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_channels.category + - id: state + type: attribute + attributes: + title: State + description: State + tags: + - Customers + sourceColumn: state + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/state + - id: date.week + type: attribute + attributes: + title: Date - Week/Year + description: Week and Year (W52/2020) + tags: + - Date + granularity: WEEK + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.week + - id: order_id + type: attribute + attributes: + title: Order id + description: Order id + tags: + - Order lines + sourceColumn: order_id + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/order_id + - id: campaign_name + type: attribute + attributes: + title: Campaign name + description: Campaign name + tags: + - Campaigns + sourceColumn: campaign_name + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_name + - id: price + type: fact + attributes: + title: Price + description: Price + tags: + - Order lines + sourceColumn: price + sourceColumnDataType: NUMERIC + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/facts/price + - id: budget_agg + type: aggregatedFact + attributes: + description: Budget Agg + tags: + - Campaign channels per category + sourceColumn: budget + sourceColumnDataType: INT + operation: SUM + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/aggregatedFacts/budget_agg + - id: date.day + type: attribute + attributes: + title: Date - Date + description: Date + tags: + - Date + granularity: DAY + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.day + - id: region + type: attribute + attributes: + title: Region + description: Region + tags: + - Customers + sourceColumn: region + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/region + - id: campaign_channel_id + type: attribute + attributes: + title: Campaign channel id + description: Campaign channel id + tags: + - Campaign channels + sourceColumn: campaign_channel_id + sourceColumnDataType: STRING + links: + self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_channel_id - id: customer_id type: attribute attributes: @@ -2732,16 +2838,6 @@ interactions: sourceColumnDataType: STRING links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/type - - id: date.quarter - type: attribute - attributes: - title: Date - Quarter/Year - description: Quarter and Year (Q1/2020) - tags: - - Date - granularity: QUARTER - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.quarter - id: spend type: fact attributes: @@ -2753,38 +2849,6 @@ interactions: sourceColumnDataType: NUMERIC links: self: http://localhost:3000/api/v1/entities/workspaces/demo/facts/spend - - id: campaign_channels.category - type: attribute - attributes: - title: Category - description: Category - tags: - - Campaign channels - sourceColumn: category - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/campaign_channels.category - - id: state - type: attribute - attributes: - title: State - description: State - tags: - - Customers - sourceColumn: state - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/state - - id: date.week - type: attribute - attributes: - title: Date - Week/Year - description: Week and Year (W52/2020) - tags: - - Date - granularity: WEEK - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/date.week - id: order_status type: attribute attributes: @@ -2796,17 +2860,6 @@ interactions: sourceColumnDataType: STRING links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/order_status - - id: order_id - type: attribute - attributes: - title: Order id - description: Order id - tags: - - Order lines - sourceColumn: order_id - sourceColumnDataType: STRING - links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/order_id - id: customer_name type: attribute attributes: @@ -2830,8 +2883,8 @@ interactions: links: self: http://localhost:3000/api/v1/entities/workspaces/demo/attributes/order_line_id links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts&page=0&size=500 - next: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts&page=1&size=500 + self: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts%2CaggregatedFacts&page=0&size=500 + next: http://localhost:3000/api/v1/entities/workspaces/demo/datasets?include=attributes%2Cfacts%2CaggregatedFacts&page=1&size=500 - request: method: GET uri: http://localhost:3000/api/v1/entities/workspaces/demo/metrics?page=0&size=500 @@ -2850,428 +2903,408 @@ interactions: code: 200 message: OK headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive Content-Length: - '10543' - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' Content-Type: - application/vnd.gooddata.api+json DATE: *id001 Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: data: - - id: percent_revenue_per_product + - id: amount_of_active_customers type: metric attributes: - title: '% Revenue per Product' + title: '# of Active Customers' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY ALL - {attribute/product_id}) + format: '#,##0' + maql: SELECT COUNT({attribute/customer_id},{attribute/order_line_id}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_per_product + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_active_customers meta: origin: originType: NATIVE originId: demo - - id: revenue + - id: amount_of_orders type: metric attributes: - title: Revenue - description: '' + title: '# of Orders' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/order_amount} WHERE NOT ({label/order_status} - IN ("Returned", "Canceled")) + format: '#,##0' + maql: SELECT COUNT({attribute/order_id}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_orders meta: origin: originType: NATIVE originId: demo - - id: revenue-clothing + - id: amount_of_top_customers type: metric attributes: - title: Revenue (Clothing) + title: '# of Top Customers' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/revenue} WHERE {label/products.category} IN - ("Clothing") + format: '#,##0' + maql: 'SELECT {metric/amount_of_active_customers} WHERE (SELECT + {metric/revenue} BY {attribute/customer_id}) > 10000 ' links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-clothing + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_top_customers meta: origin: originType: NATIVE originId: demo - - id: revenue-electronic + - id: amount_of_valid_orders type: metric attributes: - title: Revenue (Electronic) + title: '# of Valid Orders' + description: '' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/revenue} WHERE {label/products.category} IN - ( "Electronics") + format: '#,##0.00' + maql: SELECT {metric/amount_of_orders} WHERE NOT ({label/order_status} + IN ("Returned", "Canceled")) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-electronic + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_valid_orders meta: origin: originType: NATIVE originId: demo - - id: revenue-home + - id: campaign_spend type: metric attributes: - title: Revenue (Home) + title: Campaign Spend areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: format: $#,##0 - maql: SELECT {metric/revenue} WHERE {label/products.category} IN - ("Home") + maql: SELECT SUM({fact/spend}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-home + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/campaign_spend meta: origin: originType: NATIVE originId: demo - - id: revenue-outdoor + - id: order_amount type: metric attributes: - title: Revenue (Outdoor) + title: Order Amount areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: format: $#,##0 - maql: SELECT {metric/revenue} WHERE {label/products.category} IN - ("Outdoor") + maql: SELECT SUM({fact/price}*{fact/quantity}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-outdoor + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/order_amount meta: origin: originType: NATIVE originId: demo - - id: revenue_per_customer + - id: percent_revenue type: metric attributes: - title: Revenue per Customer + title: '% Revenue' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0.0 - maql: SELECT AVG(SELECT {metric/revenue} BY {attribute/customer_id}) + format: '#,##0.0%' + maql: SELECT {metric/revenue} / {metric/total_revenue} links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_per_customer + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue meta: origin: originType: NATIVE originId: demo - - id: revenue_per_dollar_spent + - id: percent_revenue_from_top_10_customers type: metric attributes: - title: Revenue per Dollar Spent + title: '% Revenue from Top 10 Customers' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0.0 - maql: SELECT {metric/revenue} / {metric/campaign_spend} + format: '#,##0.0%' + maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10}\ + \ BY {attribute/customer_id}) > 0)\n /\n {metric/revenue}" links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_per_dollar_spent + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_customers meta: origin: originType: NATIVE originId: demo - - id: revenue_top_10 + - id: percent_revenue_from_top_10_percent_customers type: metric attributes: - title: Revenue / Top 10 + title: '% Revenue from Top 10% Customers' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/revenue} WHERE TOP(10) OF ({metric/revenue}) + format: '#,##0.0%' + maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10_percent}\ + \ BY {attribute/customer_id}) > 0)\n /\n {metric/revenue}" links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_top_10 + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_percent_customers meta: origin: originType: NATIVE originId: demo - - id: revenue_top_10_percent + - id: percent_revenue_from_top_10_percent_products type: metric attributes: - title: Revenue / Top 10% + title: '% Revenue from Top 10% Products' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/revenue} WHERE TOP(10%) OF ({metric/revenue}) + format: '#,##0.0%' + maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10_percent}\ + \ BY {attribute/product_id}) > 0)\n /\n {metric/revenue}" links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_top_10_percent + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_percent_products meta: origin: originType: NATIVE originId: demo - - id: total_revenue + - id: percent_revenue_from_top_10_products type: metric attributes: - title: Total Revenue + title: '% Revenue from Top 10 Products' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/revenue} BY ALL OTHER + format: '#,##0.0%' + maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10}\ + \ BY {attribute/product_id}) > 0)\n /\n {metric/revenue}" links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/total_revenue + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_products meta: origin: originType: NATIVE originId: demo - - id: total_revenue-no_filters + - id: percent_revenue_in_category type: metric attributes: - title: Total Revenue (No Filters) + title: '% Revenue in Category' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: $#,##0 - maql: SELECT {metric/total_revenue} WITHOUT PARENT FILTER + format: '#,##0.0%' + maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY {attribute/products.category}, + ALL OTHER) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/total_revenue-no_filters + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_in_category meta: origin: originType: NATIVE originId: demo - - id: amount_of_active_customers + - id: percent_revenue_per_product type: metric attributes: - title: '# of Active Customers' + title: '% Revenue per Product' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0' - maql: SELECT COUNT({attribute/customer_id},{attribute/order_line_id}) + format: '#,##0.0%' + maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY ALL + {attribute/product_id}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_active_customers + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_per_product meta: origin: originType: NATIVE originId: demo - - id: amount_of_orders + - id: revenue type: metric attributes: - title: '# of Orders' + title: Revenue + description: '' areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0' - maql: SELECT COUNT({attribute/order_id}) + format: $#,##0 + maql: SELECT {metric/order_amount} WHERE NOT ({label/order_status} + IN ("Returned", "Canceled")) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_orders + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue meta: origin: originType: NATIVE originId: demo - - id: amount_of_top_customers + - id: revenue-clothing type: metric attributes: - title: '# of Top Customers' + title: Revenue (Clothing) areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0' - maql: 'SELECT {metric/amount_of_active_customers} WHERE (SELECT - {metric/revenue} BY {attribute/customer_id}) > 10000 ' + format: $#,##0 + maql: SELECT {metric/revenue} WHERE {label/products.category} IN + ("Clothing") links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_top_customers + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-clothing meta: origin: originType: NATIVE originId: demo - - id: amount_of_valid_orders + - id: revenue-electronic type: metric attributes: - title: '# of Valid Orders' - description: '' + title: Revenue (Electronic) areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.00' - maql: SELECT {metric/amount_of_orders} WHERE NOT ({label/order_status} - IN ("Returned", "Canceled")) + format: $#,##0 + maql: SELECT {metric/revenue} WHERE {label/products.category} IN + ( "Electronics") links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/amount_of_valid_orders + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-electronic meta: origin: originType: NATIVE originId: demo - - id: campaign_spend + - id: revenue-home type: metric attributes: - title: Campaign Spend + title: Revenue (Home) areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: format: $#,##0 - maql: SELECT SUM({fact/spend}) + maql: SELECT {metric/revenue} WHERE {label/products.category} IN + ("Home") links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/campaign_spend + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-home meta: origin: originType: NATIVE originId: demo - - id: order_amount + - id: revenue-outdoor type: metric attributes: - title: Order Amount + title: Revenue (Outdoor) areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: format: $#,##0 - maql: SELECT SUM({fact/price}*{fact/quantity}) + maql: SELECT {metric/revenue} WHERE {label/products.category} IN + ("Outdoor") links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/order_amount + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue-outdoor meta: origin: originType: NATIVE originId: demo - - id: percent_revenue + - id: revenue_per_customer type: metric attributes: - title: '% Revenue' + title: Revenue per Customer areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: SELECT {metric/revenue} / {metric/total_revenue} + format: $#,##0.0 + maql: SELECT AVG(SELECT {metric/revenue} BY {attribute/customer_id}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_per_customer meta: origin: originType: NATIVE originId: demo - - id: percent_revenue_from_top_10_customers + - id: revenue_per_dollar_spent type: metric attributes: - title: '% Revenue from Top 10 Customers' + title: Revenue per Dollar Spent areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10}\ - \ BY {attribute/customer_id}) > 0)\n /\n {metric/revenue}" + format: $#,##0.0 + maql: SELECT {metric/revenue} / {metric/campaign_spend} links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_customers + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_per_dollar_spent meta: origin: originType: NATIVE originId: demo - - id: percent_revenue_from_top_10_percent_customers + - id: revenue_top_10 type: metric attributes: - title: '% Revenue from Top 10% Customers' + title: Revenue / Top 10 areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10_percent}\ - \ BY {attribute/customer_id}) > 0)\n /\n {metric/revenue}" + format: $#,##0 + maql: SELECT {metric/revenue} WHERE TOP(10) OF ({metric/revenue}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_percent_customers + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_top_10 meta: origin: originType: NATIVE originId: demo - - id: percent_revenue_from_top_10_percent_products + - id: revenue_top_10_percent type: metric attributes: - title: '% Revenue from Top 10% Products' + title: Revenue / Top 10% areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10_percent}\ - \ BY {attribute/product_id}) > 0)\n /\n {metric/revenue}" + format: $#,##0 + maql: SELECT {metric/revenue} WHERE TOP(10%) OF ({metric/revenue}) links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_percent_products + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/revenue_top_10_percent meta: origin: originType: NATIVE originId: demo - - id: percent_revenue_from_top_10_products + - id: total_revenue type: metric attributes: - title: '% Revenue from Top 10 Products' + title: Total Revenue areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: "SELECT\n (SELECT {metric/revenue} WHERE (SELECT {metric/revenue_top_10}\ - \ BY {attribute/product_id}) > 0)\n /\n {metric/revenue}" + format: $#,##0 + maql: SELECT {metric/revenue} BY ALL OTHER links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_from_top_10_products + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/total_revenue meta: origin: originType: NATIVE originId: demo - - id: percent_revenue_in_category + - id: total_revenue-no_filters type: metric attributes: - title: '% Revenue in Category' + title: Total Revenue (No Filters) areRelationsValid: true - createdAt: 2025-08-07 13:04 + createdAt: 2025-08-07 11:45 content: - format: '#,##0.0%' - maql: SELECT {metric/revenue} / (SELECT {metric/revenue} BY {attribute/products.category}, - ALL OTHER) + format: $#,##0 + maql: SELECT {metric/total_revenue} WITHOUT PARENT FILTER links: - self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/percent_revenue_in_category + self: http://localhost:3000/api/v1/entities/workspaces/demo/metrics/total_revenue-no_filters meta: origin: originType: NATIVE @@ -5065,49 +5098,29 @@ interactions: code: 204 message: No Content headers: - Access-Control-Allow-Credentials: - - 'true' - Access-Control-Expose-Headers: - - Content-Disposition, Content-Length, Content-Range, Set-Cookie Cache-Control: - no-cache, no-store, max-age=0, must-revalidate - Connection: - - keep-alive - Content-Security-Policy: - - 'default-src ''self'' *.wistia.com *.wistia.net; script-src ''self'' ''unsafe-inline'' - ''unsafe-eval'' *.wistia.com *.wistia.net *.hsforms.net *.hsforms.com - src.litix.io matomo.anywhere.gooddata.com *.jquery.com unpkg.com cdnjs.cloudflare.com; - img-src * data: blob:; style-src ''self'' ''unsafe-inline'' fonts.googleapis.com - cdn.jsdelivr.net fast.fonts.net; font-src ''self'' data: fonts.gstatic.com - *.alicdn.com *.wistia.com cdn.jsdelivr.net info.gooddata.com; frame-src - ''self'' *.hsforms.net *.hsforms.com; object-src ''none''; worker-src - ''self'' blob:; child-src blob:; connect-src ''self'' *.tiles.mapbox.com - *.mapbox.com *.litix.io *.wistia.com *.hsforms.net *.hsforms.com embedwistia-a.akamaihd.net - matomo.anywhere.gooddata.com; media-src ''self'' blob: data: *.wistia.com - *.wistia.net embedwistia-a.akamaihd.net' DATE: *id001 Expires: - '0' - GoodData-Deployment: - - aio - Permission-Policy: - - geolocation 'none'; midi 'none'; sync-xhr 'none'; microphone 'none'; camera - 'none'; magnetometer 'none'; gyroscope 'none'; fullscreen 'none'; payment - 'none'; + Featurepolicy: + - geolocation 'none'; midi 'none'; notifications 'none'; push 'none'; sync-xhr + 'none'; microphone 'none'; camera 'none'; magnetometer 'none'; gyroscope + 'none'; speaker 'none'; vibrate 'none'; fullscreen 'none'; payment 'none'; Pragma: - no-cache Referrer-Policy: - - no-referrer - Server: - - nginx + - same-origin Vary: - Origin - Access-Control-Request-Method - Access-Control-Request-Headers X-Content-Type-Options: - nosniff + X-Frame-Options: + - SAMEORIGIN X-GDC-TRACE-ID: *id001 - X-XSS-Protection: - - '0' + X-Xss-Protection: + - 1; mode=block body: string: '' diff --git a/gooddata-sdk/tests/catalog/test_catalog_workspace.py b/gooddata-sdk/tests/catalog/test_catalog_workspace.py index df06cd1ae..321af2fe3 100644 --- a/gooddata-sdk/tests/catalog/test_catalog_workspace.py +++ b/gooddata-sdk/tests/catalog/test_catalog_workspace.py @@ -701,8 +701,9 @@ def test_clone_workspace(test_config): default_cloned_decl_ws = sdk.catalog_workspace.get_declarative_workspace(default_cloned_ws_id) assert default_cloned_decl_ws.ldm.datasets[0].data_source_table_id.data_source_id == test_config["data_source2"] assert default_cloned_decl_ws.ldm.datasets[0].facts[0].source_column == "BUDGET" - # TODO: Add a nontrivial test for agg facts here - assert default_cloned_decl_ws.ldm.datasets[0].aggregated_facts == [] + # TODO: Leaving this for todo, _refresh_workspaces will mess up with other agg fact tests + # If you fix the file in _refresh_workspaces it will mess with all the other tests + # assert default_cloned_decl_ws.ldm.datasets[1].aggregated_facts[0].source_column == "BUDGET" sdk.catalog_workspace.clone_workspace( source_ws_id, target_workspace_id=custom_cloned_ws_id, target_workspace_name=custom_cloned_ws_name @@ -756,7 +757,7 @@ def test_translate_workspace(test_config): for fact in dataset.facts: if fact.id == "budget": assert fact.title == "Rozpočet" - # TODO: Add agg facts here for descriptions? + # TODO: Do for aggregated facts descriptions # Run second time without translation function. Previous execution created translation file, which is used. sdk.catalog_workspace.generate_localized_workspaces( diff --git a/gooddata-sdk/tests/catalog/test_catalog_workspace_content.py b/gooddata-sdk/tests/catalog/test_catalog_workspace_content.py index 1c1343e31..c67cdc68b 100644 --- a/gooddata-sdk/tests/catalog/test_catalog_workspace_content.py +++ b/gooddata-sdk/tests/catalog/test_catalog_workspace_content.py @@ -63,8 +63,7 @@ def test_catalog_list_facts(test_config): def test_catalog_list_aggregated_facts(test_config): sdk = GoodDataSdk.create(host_=test_config["host"], token_=test_config["token"]) agg_facts_list = sdk.catalog_workspace_content.get_aggregated_facts_catalog(test_config["workspace"]) - # TODO: Add a non-trivial test - assert len(agg_facts_list) == 0 + assert len(agg_facts_list) == 1 @gd_vcr.use_cassette(str(_fixtures_dir / "demo_catalog_list_attributes.yaml")) @@ -129,7 +128,7 @@ def test_load_and_modify_ds_and_put_declarative_ldm(test_config): sdk.catalog_workspace.create_or_update(workspace) ldm_e = sdk.catalog_workspace_content.get_declarative_ldm(workspace_id) - ds_e = list(set([d.data_source_table_id.data_source_id for d in ldm_e.ldm.datasets])) + ds_e = list(set([d.data_source_table_id.data_source_id for d in ldm_e.ldm.datasets if d.data_source_table_id])) assert ds_e == [test_config["data_source"]] try: @@ -147,7 +146,7 @@ def test_load_and_modify_ds_and_put_declarative_ldm(test_config): ldm_e.ldm.modify_mapped_data_source(data_source_mapping=reverse_data_source_mapping) sdk.catalog_workspace_content.put_declarative_ldm(identifier, ldm_e, validator, standalone_copy=True) ldm_o = sdk.catalog_workspace_content.get_declarative_ldm(identifier) - ds_o = list(set([d.data_source_table_id.data_source_id for d in ldm_o.ldm.datasets])) + ds_o = list(set([d.data_source_table_id.data_source_id for d in ldm_o.ldm.datasets if d.data_source_table_id])) assert ds_o == [test_config["data_source"]] finally: _refresh_workspaces(sdk) @@ -163,10 +162,11 @@ def test_load_ldm_and_modify_tables_columns_case(test_config): attribute_column = "campaign_channel_id" fact_column = "budget" reference_column = "campaign_id" + assert ldm_e.ldm.datasets[0].data_source_table_id.id == table_id.upper() assert ldm_e.ldm.datasets[0].attributes[0].source_column == attribute_column.upper() assert ldm_e.ldm.datasets[0].facts[0].source_column == fact_column.upper() - # TODO: Add agg facts here + assert ldm_e.ldm.datasets[1].aggregated_facts[0].source_column == fact_column.upper() assert ldm_e.ldm.datasets[0].references[0].source_columns is None assert ldm_e.ldm.datasets[0].references[0].sources[0].column == reference_column.upper() # Test chaining approach as well @@ -178,7 +178,7 @@ def test_load_ldm_and_modify_tables_columns_case(test_config): assert ldm_o.ldm.datasets[0].data_source_table_id.id == table_id assert ldm_o.ldm.datasets[0].attributes[0].source_column == attribute_column assert ldm_o.ldm.datasets[0].facts[0].source_column == fact_column - # TODO: Add agg facts here + assert ldm_o.ldm.datasets[1].aggregated_facts[0].source_column == fact_column assert ldm_o.ldm.datasets[0].references[0].source_columns is None assert ldm_e.ldm.datasets[0].references[0].sources[0].column == reference_column @@ -313,7 +313,7 @@ def test_catalog_load(test_config): # rough initial smoke-test; just do a quick 'rub' assert len(catalog.metrics) == 24 - assert len(catalog.datasets) == 6 + assert len(catalog.datasets) == 7 assert catalog.get_metric("order_amount") is not None assert catalog.get_metric("revenue") is not None diff --git a/tests-support/fixtures/demo_declarative_hierarchy.json b/tests-support/fixtures/demo_declarative_hierarchy.json index dd4941286..b8c0c1821 100644 --- a/tests-support/fixtures/demo_declarative_hierarchy.json +++ b/tests-support/fixtures/demo_declarative_hierarchy.json @@ -2611,7 +2611,59 @@ "title": "Campaign channels" }, { - "aggregatedFacts": [], + "attributes": [], + "description": "Campaign channels per categories", + "facts": [], + "aggregatedFacts": [ + { + "description": "Budget Agg", + "id": "budget_agg", + "sourceColumn": "budget", + "sourceColumnDataType": "INT", + "tags": [ + "Campaign channels per category" + ], + "sourceFactReference": { + "reference": { + "id": "budget", + "type": "fact" + }, + "operation": "SUM" + } + } + ], + "grain": [], + "id": "campaign_channels_per_category", + "precedence": 1, + "references": [ + { + "identifier": { + "id": "campaign_channels", + "type": "dataset" + }, + "multivalue": false, + "sources": [ + { + "column": "campaign_channel_id", + "dataType": "STRING", + "target": { + "id": "campaign_channel_id", + "type": "attribute" + } + } + ] + } + ], + "tags": [ + "Campaign channels per category" + ], + "sql": { + "statement": "SELECT category, SUM(budget) FROM campaign_channels GROUP BY category", + "dataSourceId": "demo-test-ds" + }, + "title": "Campaign channels per category" + }, + { "attributes": [ { "description": "Campaign id", diff --git a/tests-support/upload_demo_layout.py b/tests-support/upload_demo_layout.py index 2f4a9bc43..543a86a85 100644 --- a/tests-support/upload_demo_layout.py +++ b/tests-support/upload_demo_layout.py @@ -35,7 +35,7 @@ def rest_op(op, url_path, data=None, raise_ex=True): if response.status_code < 200 or response.status_code > 299: if raise_ex: - raise Exception(f"Call to {url} failed - {str(response)}") + raise Exception(f"Call to {url} failed - {str(response.text)}") else: return None