jupiter-dynamic-forms 1.5.0 → 1.6.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.mjs CHANGED
@@ -592,7 +592,7 @@ class XBRLFormBuilder {
592
592
  return {
593
593
  id: role.id,
594
594
  title,
595
- description: `Section for ${title}`,
595
+ description: ``,
596
596
  concepts: conceptTrees,
597
597
  columns,
598
598
  expanded: false
@@ -904,7 +904,94 @@ class XBRLFormBuilder {
904
904
  * Generate columns for single dimension scenarios
905
905
  */
906
906
  static generateSingleDimensionColumns(dimension, periodStartDate, periodEndDate, periodTypes) {
907
- var _a, _b;
907
+ var _a, _b, _c;
908
+ if (dimension.typedMember) {
909
+ console.log(`📊 Found typed member dimension:`, {
910
+ id: dimension.id,
911
+ conceptName: dimension.conceptName,
912
+ typedMemberId: dimension.typedMember.id
913
+ });
914
+ const axisLabel2 = ((_a = dimension.labels.find((l2) => l2.role === "http://www.xbrl.org/2003/role/label")) == null ? void 0 : _a.label) || dimension.conceptName;
915
+ const typedMemberLabel = dimension.typedMember.id.split("_").pop() || "TypedMember";
916
+ const dimensionInfo2 = {
917
+ axisId: dimension.id,
918
+ axisLabel: axisLabel2,
919
+ memberId: dimension.typedMember.id,
920
+ memberLabel: typedMemberLabel,
921
+ dimensionKey: `${axisLabel2} | ${typedMemberLabel}`,
922
+ dimensionIdKey: `${dimension.id} | ${dimension.typedMember.id}`
923
+ };
924
+ console.log(`📊 Generated typed dimension info:`, dimensionInfo2);
925
+ const columns2 = [];
926
+ if (periodTypes.size === 0) {
927
+ const column = {
928
+ id: "default",
929
+ title: dimensionInfo2.memberLabel,
930
+ description: "Default typed dimension column",
931
+ type: "dimension",
932
+ dimensionData: {
933
+ dimensionId: "default",
934
+ axisId: dimensionInfo2.axisId,
935
+ memberId: dimensionInfo2.memberId,
936
+ memberValue: dimensionInfo2.memberLabel,
937
+ axisLabel: dimensionInfo2.axisLabel,
938
+ memberLabel: dimensionInfo2.memberLabel,
939
+ isTypedMember: true,
940
+ dimensionIdKey: dimensionInfo2.dimensionIdKey
941
+ },
942
+ order: 0,
943
+ removable: false
944
+ };
945
+ console.log(`📊 Generated typed member column:`, column);
946
+ columns2.push(column);
947
+ } else {
948
+ if (periodTypes.has("instant")) {
949
+ columns2.push({
950
+ id: `instant_${dimensionInfo2.axisId}_${dimensionInfo2.memberId}`,
951
+ title: `${dimensionInfo2.memberLabel} (Instant)`,
952
+ description: `${periodStartDate}`,
953
+ type: "dimension",
954
+ dimensionData: {
955
+ dimensionId: `instant_${dimensionInfo2.axisId}_${dimensionInfo2.memberId}`,
956
+ axisId: dimensionInfo2.axisId,
957
+ memberId: dimensionInfo2.memberId,
958
+ memberValue: dimensionInfo2.memberLabel,
959
+ axisLabel: dimensionInfo2.axisLabel,
960
+ memberLabel: dimensionInfo2.memberLabel,
961
+ isTypedMember: true,
962
+ dimensionIdKey: dimensionInfo2.dimensionIdKey
963
+ },
964
+ order: 0,
965
+ removable: false
966
+ });
967
+ }
968
+ if (periodTypes.has("duration")) {
969
+ columns2.push({
970
+ id: `duration_${dimensionInfo2.axisId}_${dimensionInfo2.memberId}`,
971
+ title: `${dimensionInfo2.memberLabel} (Duration)`,
972
+ description: `${periodStartDate} / ${periodEndDate}`,
973
+ type: "dimension",
974
+ dimensionData: {
975
+ dimensionId: `duration_${dimensionInfo2.axisId}_${dimensionInfo2.memberId}`,
976
+ axisId: dimensionInfo2.axisId,
977
+ memberId: dimensionInfo2.memberId,
978
+ memberValue: dimensionInfo2.memberLabel,
979
+ axisLabel: dimensionInfo2.axisLabel,
980
+ memberLabel: dimensionInfo2.memberLabel,
981
+ isTypedMember: true,
982
+ dimensionIdKey: dimensionInfo2.dimensionIdKey
983
+ },
984
+ order: 1,
985
+ removable: false
986
+ });
987
+ }
988
+ }
989
+ return columns2;
990
+ }
991
+ if (!dimension.members || !Array.isArray(dimension.members)) {
992
+ console.log(`⚠️ Dimension ${dimension.id} has no members defined, skipping column generation`);
993
+ return [];
994
+ }
908
995
  console.log(`📊 Found single dimension:`, {
909
996
  id: dimension.id,
910
997
  conceptName: dimension.conceptName,
@@ -913,9 +1000,9 @@ class XBRLFormBuilder {
913
1000
  if (dimension.members.length === 0) {
914
1001
  return [];
915
1002
  }
916
- const axisLabel = ((_a = dimension.labels.find((l2) => l2.role === "http://www.xbrl.org/2003/role/label")) == null ? void 0 : _a.label) || dimension.conceptName;
1003
+ const axisLabel = ((_b = dimension.labels.find((l2) => l2.role === "http://www.xbrl.org/2003/role/label")) == null ? void 0 : _b.label) || dimension.conceptName;
917
1004
  const firstMember = dimension.members[0];
918
- const memberLabel = ((_b = firstMember.labels.find((l2) => l2.role === "http://www.xbrl.org/2003/role/label")) == null ? void 0 : _b.label) || firstMember.conceptName;
1005
+ const memberLabel = ((_c = firstMember.labels.find((l2) => l2.role === "http://www.xbrl.org/2003/role/label")) == null ? void 0 : _c.label) || firstMember.conceptName;
919
1006
  const dimensionInfo = {
920
1007
  axisId: dimension.id,
921
1008
  axisLabel,
@@ -1033,9 +1120,38 @@ class XBRLFormBuilder {
1033
1120
  */
1034
1121
  static generateMultiDimensionColumns(dimensions, periodStartDate, periodEndDate, periodTypes) {
1035
1122
  console.log(`📊 Processing ${dimensions.length} dimensions for multi-dimensional columns`);
1036
- const dimensionInfos = dimensions.map((dimension) => {
1123
+ const validDimensions = dimensions.filter((dimension) => {
1124
+ if (dimension.typedMember) {
1125
+ return true;
1126
+ }
1127
+ if (!dimension.members || !Array.isArray(dimension.members) || dimension.members.length === 0) {
1128
+ console.log(`⚠️ Skipping dimension ${dimension.id} - no members defined`);
1129
+ return false;
1130
+ }
1131
+ return true;
1132
+ });
1133
+ if (validDimensions.length === 0) {
1134
+ console.log(`⚠️ No valid dimensions with members found, skipping multi-dimensional column generation`);
1135
+ return [];
1136
+ }
1137
+ const dimensionInfos = validDimensions.map((dimension) => {
1037
1138
  var _a;
1038
1139
  const axisLabel = ((_a = dimension.labels.find((l2) => l2.role === "http://www.xbrl.org/2003/role/label")) == null ? void 0 : _a.label) || dimension.conceptName;
1140
+ if (dimension.typedMember) {
1141
+ const typedMemberLabel = dimension.typedMember.id.split("_").pop() || "TypedMember";
1142
+ return {
1143
+ id: dimension.id,
1144
+ axisLabel,
1145
+ isTypedDimension: true,
1146
+ // Flag to track typed dimensions
1147
+ members: [{
1148
+ id: dimension.typedMember.id,
1149
+ label: typedMemberLabel,
1150
+ isTypedMember: true
1151
+ // Flag for the member itself
1152
+ }]
1153
+ };
1154
+ }
1039
1155
  const allMembers = this.getAllDimensionMembers(dimension.members);
1040
1156
  return {
1041
1157
  id: dimension.id,
@@ -1054,17 +1170,21 @@ class XBRLFormBuilder {
1054
1170
  const columns = [];
1055
1171
  combinations.forEach((combination, index) => {
1056
1172
  const columnTitle = combination.map((c2) => c2.memberLabel).join(" | ");
1173
+ const hasTypedMembers = combination.some((c2) => c2.isTypedMember);
1057
1174
  const dimensionData = {
1058
1175
  dimensionId: `multi_${index}`,
1059
1176
  memberValue: columnTitle,
1060
1177
  // Required field
1061
1178
  memberLabel: columnTitle,
1062
1179
  // Required field
1180
+ isTypedMember: hasTypedMembers,
1181
+ // Flag if any dimension in combination is typed
1063
1182
  combinations: combination.map((c2) => ({
1064
1183
  axisId: c2.axisId,
1065
1184
  axisLabel: c2.axisLabel,
1066
1185
  memberId: c2.memberId,
1067
- memberLabel: c2.memberLabel
1186
+ memberLabel: c2.memberLabel,
1187
+ isTypedMember: c2.isTypedMember || false
1068
1188
  })),
1069
1189
  memberKey: columnTitle,
1070
1190
  dimensionIdKey: combination.map((c2) => `${c2.axisId}|${c2.memberId}`).join("::")
@@ -1129,6 +1249,9 @@ class XBRLFormBuilder {
1129
1249
  * Get all members including children recursively
1130
1250
  */
1131
1251
  static getAllDimensionMembers(members) {
1252
+ if (!members || !Array.isArray(members)) {
1253
+ return [];
1254
+ }
1132
1255
  const allMembers = [];
1133
1256
  members.forEach((member) => {
1134
1257
  allMembers.push(member);
@@ -2150,6 +2273,7 @@ let JupiterFormSection = class extends LitElement {
2150
2273
  this._expanded = true;
2151
2274
  this._showAddColumnDialog = false;
2152
2275
  this._sectionPeriodType = "duration";
2276
+ this._typedMemberValues = {};
2153
2277
  this._expandedConcepts = /* @__PURE__ */ new Set();
2154
2278
  }
2155
2279
  connectedCallback() {
@@ -2277,6 +2401,14 @@ let JupiterFormSection = class extends LitElement {
2277
2401
  bubbles: true
2278
2402
  }));
2279
2403
  }
2404
+ _handleTypedMemberValueChange(columnId, value) {
2405
+ this._typedMemberValues[columnId] = value;
2406
+ this.dispatchEvent(new CustomEvent("typed-member-change", {
2407
+ detail: { columnId, value, sectionId: this.section.id },
2408
+ bubbles: true
2409
+ }));
2410
+ this.requestUpdate();
2411
+ }
2280
2412
  _flattenConcepts(concepts, expanded = /* @__PURE__ */ new Set()) {
2281
2413
  const result = [];
2282
2414
  for (const concept of concepts) {
@@ -2345,22 +2477,36 @@ let JupiterFormSection = class extends LitElement {
2345
2477
  <thead class="table-header">
2346
2478
  <tr class="header-row">
2347
2479
  <th class="header-cell concept-column">Concept</th>
2348
- ${this.columns.map((column) => html`
2480
+ ${this.columns.map((column) => {
2481
+ var _a;
2482
+ return html`
2349
2483
  <th class="header-cell ${column.removable ? "removable" : ""}">
2350
2484
  ${column.title}
2351
2485
  ${column.description ? html`<div style="font-weight: normal; font-size: 12px; color: var(--jupiter-text-secondary, #666);">${column.description}</div>` : ""}
2486
+ ${((_a = column.dimensionData) == null ? void 0 : _a.isTypedMember) ? html`
2487
+ <div style="margin-top: 8px;">
2488
+ <input
2489
+ type="text"
2490
+ placeholder="Enter typed member value"
2491
+ .value="${this._typedMemberValues[column.id] || ""}"
2492
+ @input="${(e2) => this._handleTypedMemberValueChange(column.id, e2.target.value)}"
2493
+ style="width: 100%; padding: 4px; border: 1px solid #ccc; border-radius: 3px; font-size: 12px;"
2494
+ />
2495
+ </div>
2496
+ ` : ""}
2352
2497
  ${column.removable ? html`
2353
2498
  <button
2354
2499
  class="remove-column-btn"
2355
2500
  @click="${(e2) => {
2356
- e2.stopPropagation();
2357
- this._handleRemoveColumn(column.id);
2358
- }}"
2501
+ e2.stopPropagation();
2502
+ this._handleRemoveColumn(column.id);
2503
+ }}"
2359
2504
  title="Remove column"
2360
2505
  >×</button>
2361
2506
  ` : ""}
2362
2507
  </th>
2363
- `)}
2508
+ `;
2509
+ })}
2364
2510
  <th class="header-cell">
2365
2511
  <button class="add-column-btn" @click="${(e2) => {
2366
2512
  e2.stopPropagation();
@@ -2593,6 +2739,9 @@ __decorateClass$1([
2593
2739
  __decorateClass$1([
2594
2740
  r()
2595
2741
  ], JupiterFormSection.prototype, "_sectionPeriodType", 2);
2742
+ __decorateClass$1([
2743
+ r()
2744
+ ], JupiterFormSection.prototype, "_typedMemberValues", 2);
2596
2745
  __decorateClass$1([
2597
2746
  r()
2598
2747
  ], JupiterFormSection.prototype, "_expandedConcepts", 2);
@@ -2626,6 +2775,7 @@ let JupiterDynamicForm = class extends LitElement {
2626
2775
  this._dirty = false;
2627
2776
  this._valid = true;
2628
2777
  this._submitted = false;
2778
+ this._typedMemberValues = {};
2629
2779
  }
2630
2780
  connectedCallback() {
2631
2781
  super.connectedCallback();
@@ -2738,6 +2888,16 @@ let JupiterDynamicForm = class extends LitElement {
2738
2888
  bubbles: true
2739
2889
  }));
2740
2890
  }
2891
+ _handleTypedMemberChange(event) {
2892
+ const { columnId, value, sectionId } = event.detail;
2893
+ this._typedMemberValues[columnId] = value;
2894
+ this._dirty = true;
2895
+ this.requestUpdate();
2896
+ this.dispatchEvent(new CustomEvent("typed-member-change", {
2897
+ detail: { columnId, value, sectionId },
2898
+ bubbles: true
2899
+ }));
2900
+ }
2741
2901
  _handleSectionExpand(event) {
2742
2902
  this.dispatchEvent(new CustomEvent("section-expand", {
2743
2903
  detail: event.detail,
@@ -2781,7 +2941,7 @@ let JupiterDynamicForm = class extends LitElement {
2781
2941
  this._addColumnFromRequest(columnRequest, sectionId);
2782
2942
  }
2783
2943
  _addColumnFromRequest(request, sectionId) {
2784
- var _a, _b, _c, _d, _e;
2944
+ var _a, _b, _c, _d, _e, _f;
2785
2945
  const timestamp = Date.now();
2786
2946
  const newColumnId = `col-${timestamp}`;
2787
2947
  let title = "";
@@ -2804,10 +2964,28 @@ let JupiterDynamicForm = class extends LitElement {
2804
2964
  const item = hypercubeRole.items[0];
2805
2965
  if (item.dimensions.length === 1) {
2806
2966
  const dimension = item.dimensions[0];
2807
- if (dimension.members.length > 0) {
2967
+ if (dimension.typedMember) {
2808
2968
  const axisLabel = ((_d = dimension.labels.find((l2) => l2.role === "http://www.xbrl.org/2003/role/label")) == null ? void 0 : _d.label) || dimension.conceptName;
2969
+ const typedMemberLabel = dimension.typedMember.id.split("_").pop() || "TypedMember";
2970
+ const periodPart = request.periodType === "instant" ? `(${request.instantDate})` : `(${request.startDate} / ${request.endDate})`;
2971
+ title = `${typedMemberLabel} ${periodPart}`;
2972
+ dimensionData = {
2973
+ dimensionId: newColumnId,
2974
+ axisId: dimension.id,
2975
+ memberId: dimension.typedMember.id,
2976
+ memberValue: typedMemberLabel,
2977
+ memberLabel: typedMemberLabel,
2978
+ axis: axisLabel,
2979
+ axisLabel,
2980
+ memberKey: `${axisLabel} | ${typedMemberLabel}`,
2981
+ dimensionIdKey: `${dimension.id} | ${dimension.typedMember.id}`,
2982
+ isTypedMember: true
2983
+ };
2984
+ console.log(`📊 Applied typed member dimension to new column: ${dimensionData.memberKey}`);
2985
+ } else if (dimension.members && dimension.members.length > 0) {
2986
+ const axisLabel = ((_e = dimension.labels.find((l2) => l2.role === "http://www.xbrl.org/2003/role/label")) == null ? void 0 : _e.label) || dimension.conceptName;
2809
2987
  const firstMember = dimension.members[0];
2810
- const memberLabel = ((_e = firstMember.labels.find((l2) => l2.role === "http://www.xbrl.org/2003/role/label")) == null ? void 0 : _e.label) || firstMember.conceptName;
2988
+ const memberLabel = ((_f = firstMember.labels.find((l2) => l2.role === "http://www.xbrl.org/2003/role/label")) == null ? void 0 : _f.label) || firstMember.conceptName;
2811
2989
  const periodPart = request.periodType === "instant" ? `(${request.instantDate})` : `(${request.startDate} / ${request.endDate})`;
2812
2990
  title = `${memberLabel} ${periodPart}`;
2813
2991
  dimensionData = {
@@ -3029,11 +3207,18 @@ let JupiterDynamicForm = class extends LitElement {
3029
3207
  concepts.forEach((concept) => {
3030
3208
  if (concept.fields && concept.fields.length > 0) {
3031
3209
  concept.fields.forEach((field) => {
3032
- var _a, _b, _c;
3210
+ var _a, _b, _c, _d;
3033
3211
  const conceptData = this._formData[concept.id];
3034
3212
  const fieldValue = conceptData == null ? void 0 : conceptData[field.columnId];
3035
3213
  if (fieldValue !== void 0 && fieldValue !== null && fieldValue !== "") {
3036
3214
  const column = this._findColumnById(field.columnId);
3215
+ console.log(`🔍 Processing field for concept ${concept.id}:`, {
3216
+ fieldColumnId: field.columnId,
3217
+ foundColumn: column,
3218
+ columnType: column == null ? void 0 : column.type,
3219
+ dimensionData: column == null ? void 0 : column.dimensionData,
3220
+ isTypedMember: (_a = column == null ? void 0 : column.dimensionData) == null ? void 0 : _a.isTypedMember
3221
+ });
3037
3222
  const submissionEntry = {
3038
3223
  conceptId: concept.id,
3039
3224
  value: fieldValue,
@@ -3047,15 +3232,43 @@ let JupiterDynamicForm = class extends LitElement {
3047
3232
  submissionEntry.period.startDate = field.periodStartDate || this.periodStartDate;
3048
3233
  submissionEntry.period.endDate = field.periodEndDate || this.periodEndDate;
3049
3234
  }
3050
- if ((column == null ? void 0 : column.type) === "dimension" && ((_a = column.dimensionData) == null ? void 0 : _a.dimensionIdKey)) {
3051
- submissionEntry.dimension = column.dimensionData.dimensionIdKey;
3052
- } else if ((_b = section == null ? void 0 : section.columns) == null ? void 0 : _b.length) {
3235
+ if ((column == null ? void 0 : column.type) === "dimension" && ((_b = column.dimensionData) == null ? void 0 : _b.dimensionIdKey)) {
3236
+ console.log(`✅ Found column dimension data:`, column.dimensionData);
3237
+ if (column.dimensionData.isTypedMember) {
3238
+ submissionEntry.dimension = column.dimensionData.dimensionIdKey;
3239
+ submissionEntry.typedDimension = true;
3240
+ submissionEntry.typedMemberValue = this._typedMemberValues[column.id] || "";
3241
+ } else {
3242
+ submissionEntry.dimension = column.dimensionData.dimensionIdKey;
3243
+ }
3244
+ } else if ((_c = section == null ? void 0 : section.columns) == null ? void 0 : _c.length) {
3245
+ console.log(`🔍 Checking section columns for dimension data:`, {
3246
+ sectionId: section.id,
3247
+ columnsCount: section.columns.length,
3248
+ columns: section.columns.map((col) => {
3249
+ var _a2, _b2;
3250
+ return {
3251
+ id: col.id,
3252
+ type: col.type,
3253
+ hasDimensionData: !!col.dimensionData,
3254
+ dimensionIdKey: (_a2 = col.dimensionData) == null ? void 0 : _a2.dimensionIdKey,
3255
+ isTypedMember: (_b2 = col.dimensionData) == null ? void 0 : _b2.isTypedMember
3256
+ };
3257
+ })
3258
+ });
3053
3259
  const sectionDimensionColumn = section.columns.find((col) => {
3054
3260
  var _a2;
3055
3261
  return col.type === "dimension" && ((_a2 = col.dimensionData) == null ? void 0 : _a2.dimensionIdKey);
3056
3262
  });
3057
- if ((_c = sectionDimensionColumn == null ? void 0 : sectionDimensionColumn.dimensionData) == null ? void 0 : _c.dimensionIdKey) {
3058
- submissionEntry.dimension = sectionDimensionColumn.dimensionData.dimensionIdKey;
3263
+ if ((_d = sectionDimensionColumn == null ? void 0 : sectionDimensionColumn.dimensionData) == null ? void 0 : _d.dimensionIdKey) {
3264
+ console.log(`✅ Found section dimension data:`, sectionDimensionColumn.dimensionData);
3265
+ if (sectionDimensionColumn.dimensionData.isTypedMember) {
3266
+ submissionEntry.dimension = sectionDimensionColumn.dimensionData.dimensionIdKey;
3267
+ submissionEntry.typedDimension = true;
3268
+ submissionEntry.typedMemberValue = this._typedMemberValues[sectionDimensionColumn.id] || "";
3269
+ } else {
3270
+ submissionEntry.dimension = sectionDimensionColumn.dimensionData.dimensionIdKey;
3271
+ }
3059
3272
  }
3060
3273
  }
3061
3274
  submissionData.push(submissionEntry);
@@ -3151,6 +3364,7 @@ let JupiterDynamicForm = class extends LitElement {
3151
3364
  .collapsible="${config.collapsibleSections !== false}"
3152
3365
  .locale="${config.locale || "en-US"}"
3153
3366
  @field-change="${this._handleFieldChange}"
3367
+ @typed-member-change="${this._handleTypedMemberChange}"
3154
3368
  @section-expand="${this._handleSectionExpand}"
3155
3369
  @concept-expand="${this._handleConceptExpand}"
3156
3370
  @column-remove="${this._handleColumnRemove}"
@@ -3366,6 +3580,9 @@ __decorateClass([
3366
3580
  __decorateClass([
3367
3581
  r()
3368
3582
  ], JupiterDynamicForm.prototype, "_currentSchema", 2);
3583
+ __decorateClass([
3584
+ r()
3585
+ ], JupiterDynamicForm.prototype, "_typedMemberValues", 2);
3369
3586
  JupiterDynamicForm = __decorateClass([
3370
3587
  t$1("jupiter-dynamic-form")
3371
3588
  ], JupiterDynamicForm);