@fluidframework/container-runtime 2.0.0-internal.3.3.1 → 2.0.0-internal.3.4.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.
Files changed (83) hide show
  1. package/dist/blobManager.d.ts +17 -11
  2. package/dist/blobManager.d.ts.map +1 -1
  3. package/dist/blobManager.js +89 -58
  4. package/dist/blobManager.js.map +1 -1
  5. package/dist/containerRuntime.d.ts +5 -0
  6. package/dist/containerRuntime.d.ts.map +1 -1
  7. package/dist/containerRuntime.js +11 -10
  8. package/dist/containerRuntime.js.map +1 -1
  9. package/dist/gc/garbageCollection.d.ts.map +1 -1
  10. package/dist/gc/garbageCollection.js +4 -5
  11. package/dist/gc/garbageCollection.js.map +1 -1
  12. package/dist/gc/gcConfigs.d.ts.map +1 -1
  13. package/dist/gc/gcConfigs.js +25 -22
  14. package/dist/gc/gcConfigs.js.map +1 -1
  15. package/dist/gc/gcDefinitions.d.ts +28 -3
  16. package/dist/gc/gcDefinitions.d.ts.map +1 -1
  17. package/dist/gc/gcDefinitions.js +15 -2
  18. package/dist/gc/gcDefinitions.js.map +1 -1
  19. package/dist/gc/gcHelpers.d.ts +25 -5
  20. package/dist/gc/gcHelpers.d.ts.map +1 -1
  21. package/dist/gc/gcHelpers.js +38 -5
  22. package/dist/gc/gcHelpers.js.map +1 -1
  23. package/dist/gc/gcSummaryStateTracker.d.ts +5 -7
  24. package/dist/gc/gcSummaryStateTracker.d.ts.map +1 -1
  25. package/dist/gc/gcSummaryStateTracker.js +16 -25
  26. package/dist/gc/gcSummaryStateTracker.js.map +1 -1
  27. package/dist/gc/index.d.ts +2 -2
  28. package/dist/gc/index.d.ts.map +1 -1
  29. package/dist/gc/index.js +3 -1
  30. package/dist/gc/index.js.map +1 -1
  31. package/dist/packageVersion.d.ts +1 -1
  32. package/dist/packageVersion.js +1 -1
  33. package/dist/packageVersion.js.map +1 -1
  34. package/dist/summary/summaryFormat.d.ts +2 -0
  35. package/dist/summary/summaryFormat.d.ts.map +1 -1
  36. package/dist/summary/summaryFormat.js.map +1 -1
  37. package/lib/blobManager.d.ts +17 -11
  38. package/lib/blobManager.d.ts.map +1 -1
  39. package/lib/blobManager.js +89 -58
  40. package/lib/blobManager.js.map +1 -1
  41. package/lib/containerRuntime.d.ts +5 -0
  42. package/lib/containerRuntime.d.ts.map +1 -1
  43. package/lib/containerRuntime.js +11 -10
  44. package/lib/containerRuntime.js.map +1 -1
  45. package/lib/gc/garbageCollection.d.ts.map +1 -1
  46. package/lib/gc/garbageCollection.js +4 -5
  47. package/lib/gc/garbageCollection.js.map +1 -1
  48. package/lib/gc/gcConfigs.d.ts.map +1 -1
  49. package/lib/gc/gcConfigs.js +25 -22
  50. package/lib/gc/gcConfigs.js.map +1 -1
  51. package/lib/gc/gcDefinitions.d.ts +28 -3
  52. package/lib/gc/gcDefinitions.d.ts.map +1 -1
  53. package/lib/gc/gcDefinitions.js +14 -1
  54. package/lib/gc/gcDefinitions.js.map +1 -1
  55. package/lib/gc/gcHelpers.d.ts +25 -5
  56. package/lib/gc/gcHelpers.d.ts.map +1 -1
  57. package/lib/gc/gcHelpers.js +36 -4
  58. package/lib/gc/gcHelpers.js.map +1 -1
  59. package/lib/gc/gcSummaryStateTracker.d.ts +5 -7
  60. package/lib/gc/gcSummaryStateTracker.d.ts.map +1 -1
  61. package/lib/gc/gcSummaryStateTracker.js +16 -25
  62. package/lib/gc/gcSummaryStateTracker.js.map +1 -1
  63. package/lib/gc/index.d.ts +2 -2
  64. package/lib/gc/index.d.ts.map +1 -1
  65. package/lib/gc/index.js +2 -2
  66. package/lib/gc/index.js.map +1 -1
  67. package/lib/packageVersion.d.ts +1 -1
  68. package/lib/packageVersion.js +1 -1
  69. package/lib/packageVersion.js.map +1 -1
  70. package/lib/summary/summaryFormat.d.ts +2 -0
  71. package/lib/summary/summaryFormat.d.ts.map +1 -1
  72. package/lib/summary/summaryFormat.js.map +1 -1
  73. package/package.json +23 -24
  74. package/src/blobManager.ts +108 -77
  75. package/src/containerRuntime.ts +12 -4
  76. package/src/gc/garbageCollection.ts +4 -8
  77. package/src/gc/gcConfigs.ts +26 -12
  78. package/src/gc/gcDefinitions.ts +28 -3
  79. package/src/gc/gcHelpers.ts +45 -4
  80. package/src/gc/gcSummaryStateTracker.ts +17 -29
  81. package/src/gc/index.ts +3 -0
  82. package/src/packageVersion.ts +1 -1
  83. package/src/summary/summaryFormat.ts +2 -0
@@ -1 +1 @@
1
- {"version":3,"file":"gcConfigs.js","sourceRoot":"","sources":["../../src/gc/gcConfigs.ts"],"names":[],"mappings":"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","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n */\n\nimport { UsageError } from \"@fluidframework/driver-utils\";\nimport { MonitoringContext } from \"@fluidframework/telemetry-utils\";\nimport { IContainerRuntimeMetadata } from \"../summary\";\nimport {\n\tdefaultInactiveTimeoutMs,\n\tdefaultSessionExpiryDurationMs,\n\tdisableTombstoneKey,\n\tGCFeatureMatrix,\n\tgcTestModeKey,\n\tgcTombstoneGenerationOptionName,\n\tGCVersion,\n\tIGarbageCollectorConfigs,\n\tIGCRuntimeOptions,\n\tmaxSnapshotCacheExpiryMs,\n\toneDayMs,\n\trunGCKey,\n\trunSessionExpiryKey,\n\trunSweepKey,\n} from \"./gcDefinitions\";\nimport { getGCVersion } from \"./gcHelpers\";\n\n/**\n * Generates configurations for the Garbage Collector that it uses to determine what to run and how.\n * @param mc - The monitoring context for reading configs from the config provider.\n * @param createParams - The creation params:\n * gcOptions - The garbage collector runtime options.\n * metadata - The container runtime's createParams.metadata.\n * existing - Whether the container is new or an existing one.\n * @returns The garbage collector configurations.\n */\nexport function generateGCConfigs(\n\tmc: MonitoringContext,\n\tcreateParams: {\n\t\tgcOptions: IGCRuntimeOptions;\n\t\tmetadata: IContainerRuntimeMetadata | undefined;\n\t\texisting: boolean;\n\t},\n): IGarbageCollectorConfigs {\n\tlet gcEnabled: boolean;\n\tlet sweepEnabled: boolean;\n\tlet sessionExpiryTimeoutMs: number | undefined;\n\tlet sweepTimeoutMs: number | undefined;\n\tlet persistedGcFeatureMatrix: GCFeatureMatrix | undefined;\n\tlet gcVersionInBaseSnapshot: GCVersion | undefined;\n\n\t/**\n\t * The following GC state is enabled during container creation and cannot be changed throughout its lifetime:\n\t * 1. Whether running GC mark phase is allowed or not.\n\t * 2. Whether running GC sweep phase is allowed or not.\n\t * 3. Whether GC session expiry is enabled or not.\n\t * For existing containers, we get this information from the createParams.metadata blob of its summary.\n\t */\n\tif (createParams.existing) {\n\t\tgcVersionInBaseSnapshot = getGCVersion(createParams.metadata);\n\t\t// Existing documents which did not have createParams.metadata blob or had GC disabled have version as 0. For all\n\t\t// other existing documents, GC is enabled.\n\t\tgcEnabled = gcVersionInBaseSnapshot > 0;\n\t\tsweepEnabled = createParams.metadata?.sweepEnabled ?? false;\n\t\tsessionExpiryTimeoutMs = createParams.metadata?.sessionExpiryTimeoutMs;\n\t\tsweepTimeoutMs =\n\t\t\tcreateParams.metadata?.sweepTimeoutMs ?? computeSweepTimeout(sessionExpiryTimeoutMs); // Backfill old documents that didn't persist this\n\t\tpersistedGcFeatureMatrix = createParams.metadata?.gcFeatureMatrix;\n\t} else {\n\t\t// Sweep should not be enabled without enabling GC mark phase. We could silently disable sweep in this\n\t\t// scenario but explicitly failing makes it clearer and promotes correct usage.\n\t\tif (createParams.gcOptions.sweepAllowed && createParams.gcOptions.gcAllowed === false) {\n\t\t\tthrow new UsageError(\"GC sweep phase cannot be enabled without enabling GC mark phase\");\n\t\t}\n\n\t\t// This Test Override only applies for new containers\n\t\tconst testOverrideSweepTimeoutMs = mc.config.getNumber(\n\t\t\t\"Fluid.GarbageCollection.TestOverride.SweepTimeoutMs\",\n\t\t);\n\n\t\t// For new documents, GC is enabled by default. It can be explicitly disabled by setting the gcAllowed\n\t\t// flag in GC options to false.\n\t\tgcEnabled = createParams.gcOptions.gcAllowed !== false;\n\t\t// The sweep phase has to be explicitly enabled by setting the sweepAllowed flag in GC options to true.\n\t\tsweepEnabled = createParams.gcOptions.sweepAllowed === true;\n\n\t\t// Set the Session Expiry if GC is enabled and session expiry flag isn't explicitly set to false.\n\t\tif (gcEnabled && mc.config.getBoolean(runSessionExpiryKey) !== false) {\n\t\t\tsessionExpiryTimeoutMs =\n\t\t\t\tcreateParams.gcOptions.sessionExpiryTimeoutMs ?? defaultSessionExpiryDurationMs;\n\t\t}\n\t\tsweepTimeoutMs = testOverrideSweepTimeoutMs ?? computeSweepTimeout(sessionExpiryTimeoutMs);\n\n\t\tif (createParams.gcOptions[gcTombstoneGenerationOptionName] !== undefined) {\n\t\t\tpersistedGcFeatureMatrix = {\n\t\t\t\ttombstoneGeneration: createParams.gcOptions[gcTombstoneGenerationOptionName],\n\t\t\t};\n\t\t}\n\t}\n\n\t/**\n\t * Whether GC should run or not. The following conditions have to be met to run sweep:\n\t *\n\t * 1. GC should be enabled for this container.\n\t *\n\t * 2. GC should not be disabled via disableGC GC option.\n\t *\n\t * These conditions can be overridden via runGCKey feature flag.\n\t */\n\tconst shouldRunGC =\n\t\tmc.config.getBoolean(runGCKey) ??\n\t\t// GC must be enabled for the document.\n\t\t(gcEnabled &&\n\t\t\t// GC must not be disabled via GC options.\n\t\t\t!createParams.gcOptions.disableGC);\n\n\t/**\n\t * Whether sweep should run or not. The following conditions have to be met to run sweep:\n\t *\n\t * 1. Overall GC or mark phase must be enabled (this.configs.shouldRunGC).\n\t * 2. Sweep timeout should be available. Without this, we wouldn't know when an object should be deleted.\n\t * 3. The driver must implement the policy limiting the age of snapshots used for loading. Otherwise\n\t * the Sweep Timeout calculation is not valid. We use the persisted value to ensure consistency over time.\n\t * 4. Sweep should be enabled for this container (this.sweepEnabled). This can be overridden via runSweep\n\t * feature flag.\n\t */\n\tconst shouldRunSweep =\n\t\tshouldRunGC &&\n\t\tsweepTimeoutMs !== undefined &&\n\t\t(mc.config.getBoolean(runSweepKey) ?? sweepEnabled);\n\n\t// Override inactive timeout if test config or gc options to override it is set.\n\tconst inactiveTimeoutMs =\n\t\tmc.config.getNumber(\"Fluid.GarbageCollection.TestOverride.InactiveTimeoutMs\") ??\n\t\tcreateParams.gcOptions.inactiveTimeoutMs ??\n\t\tdefaultInactiveTimeoutMs;\n\n\t// Inactive timeout must be greater than sweep timeout since a node goes from active -> inactive -> sweep ready.\n\tif (sweepTimeoutMs !== undefined && inactiveTimeoutMs > sweepTimeoutMs) {\n\t\tthrow new UsageError(\"inactive timeout should not be greater than the sweep timeout\");\n\t}\n\n\t// Whether we are running in test mode. In this mode, unreferenced nodes are immediately deleted.\n\tconst testMode =\n\t\tmc.config.getBoolean(gcTestModeKey) ?? createParams.gcOptions.runGCInTestMode === true;\n\t// Whether we are running in tombstone mode. This is enabled by default if sweep won't run. It can be disabled\n\t// via feature flags.\n\tconst tombstoneMode = !shouldRunSweep && mc.config.getBoolean(disableTombstoneKey) !== true;\n\tconst runFullGC = createParams.gcOptions.runFullGC;\n\n\treturn {\n\t\tgcEnabled,\n\t\tsweepEnabled,\n\t\tshouldRunGC,\n\t\tshouldRunSweep,\n\t\trunFullGC,\n\t\ttestMode,\n\t\ttombstoneMode,\n\t\tsessionExpiryTimeoutMs,\n\t\tsweepTimeoutMs,\n\t\tinactiveTimeoutMs,\n\t\tpersistedGcFeatureMatrix,\n\t\tgcVersionInBaseSnapshot,\n\t};\n}\n\n/**\n * Sweep timeout is the time after which unreferenced content can be swept.\n * Sweep timeout = session expiry timeout + snapshot cache expiry timeout + one day buffer.\n *\n * The snapshot cache expiry timeout cannot be known precisely but the upper bound is 5 days.\n * The buffer is added to account for any clock skew or other edge cases.\n * We use server timestamps throughout so the skew should be minimal but make it 1 day to be safe.\n */\nfunction computeSweepTimeout(sessionExpiryTimeoutMs: number | undefined): number | undefined {\n\tconst bufferMs = oneDayMs;\n\treturn sessionExpiryTimeoutMs && sessionExpiryTimeoutMs + maxSnapshotCacheExpiryMs + bufferMs;\n}\n"]}
1
+ {"version":3,"file":"gcConfigs.js","sourceRoot":"","sources":["../../src/gc/gcConfigs.ts"],"names":[],"mappings":"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","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n */\n\nimport { UsageError } from \"@fluidframework/container-utils\";\nimport { MonitoringContext } from \"@fluidframework/telemetry-utils\";\nimport { IContainerRuntimeMetadata } from \"../summary\";\nimport {\n\tcurrentGCVersion,\n\tdefaultInactiveTimeoutMs,\n\tdefaultSessionExpiryDurationMs,\n\tdisableTombstoneKey,\n\tGCFeatureMatrix,\n\tgcSweepGenerationOptionName,\n\tgcTestModeKey,\n\tgcTombstoneGenerationOptionName,\n\tGCVersion,\n\tgcVersionUpgradeToV2Key,\n\tIGarbageCollectorConfigs,\n\tIGCRuntimeOptions,\n\tmaxSnapshotCacheExpiryMs,\n\toneDayMs,\n\trunGCKey,\n\trunSessionExpiryKey,\n\trunSweepKey,\n\tstableGCVersion,\n} from \"./gcDefinitions\";\nimport { getGCVersion, shouldAllowGcSweep } from \"./gcHelpers\";\n\n/**\n * Generates configurations for the Garbage Collector that it uses to determine what to run and how.\n * @param mc - The monitoring context for reading configs from the config provider.\n * @param createParams - The creation params:\n * gcOptions - The garbage collector runtime options.\n * metadata - The container runtime's createParams.metadata.\n * existing - Whether the container is new or an existing one.\n * @returns The garbage collector configurations.\n */\nexport function generateGCConfigs(\n\tmc: MonitoringContext,\n\tcreateParams: {\n\t\tgcOptions: IGCRuntimeOptions;\n\t\tmetadata: IContainerRuntimeMetadata | undefined;\n\t\texisting: boolean;\n\t},\n): IGarbageCollectorConfigs {\n\tlet gcEnabled: boolean;\n\tlet sessionExpiryTimeoutMs: number | undefined;\n\tlet sweepTimeoutMs: number | undefined;\n\tlet persistedGcFeatureMatrix: GCFeatureMatrix | undefined;\n\tlet gcVersionInBaseSnapshot: GCVersion | undefined;\n\n\t/**\n\t * The following GC state is enabled during container creation and cannot be changed throughout its lifetime:\n\t * 1. Whether running GC mark phase is allowed or not.\n\t * 2. Whether running GC sweep phase is allowed or not.\n\t * 3. Whether GC session expiry is enabled or not.\n\t * For existing containers, we get this information from the createParams.metadata blob of its summary.\n\t */\n\tif (createParams.existing) {\n\t\tgcVersionInBaseSnapshot = getGCVersion(createParams.metadata);\n\t\t// Existing documents which did not have createParams.metadata blob or had GC disabled have version as 0. For all\n\t\t// other existing documents, GC is enabled.\n\t\tgcEnabled = gcVersionInBaseSnapshot > 0;\n\t\tsessionExpiryTimeoutMs = createParams.metadata?.sessionExpiryTimeoutMs;\n\t\tsweepTimeoutMs =\n\t\t\tcreateParams.metadata?.sweepTimeoutMs ?? computeSweepTimeout(sessionExpiryTimeoutMs); // Backfill old documents that didn't persist this\n\t\tpersistedGcFeatureMatrix = createParams.metadata?.gcFeatureMatrix;\n\t} else {\n\t\tconst tombstoneGeneration = createParams.gcOptions[gcTombstoneGenerationOptionName];\n\t\tconst sweepGeneration = createParams.gcOptions[gcSweepGenerationOptionName];\n\n\t\t// Sweep should not be enabled (via sweepGeneration value) without enabling GC mark phase.\n\t\tif (sweepGeneration !== undefined && createParams.gcOptions.gcAllowed === false) {\n\t\t\tthrow new UsageError(\"GC sweep phase cannot be enabled without enabling GC mark phase\");\n\t\t}\n\n\t\t// This Test Override only applies for new containers\n\t\tconst testOverrideSweepTimeoutMs = mc.config.getNumber(\n\t\t\t\"Fluid.GarbageCollection.TestOverride.SweepTimeoutMs\",\n\t\t);\n\n\t\t// For new documents, GC is enabled by default. It can be explicitly disabled by setting the gcAllowed\n\t\t// flag in GC options to false.\n\t\tgcEnabled = createParams.gcOptions.gcAllowed !== false;\n\n\t\t// Set the Session Expiry if GC is enabled and session expiry flag isn't explicitly set to false.\n\t\tif (gcEnabled && mc.config.getBoolean(runSessionExpiryKey) !== false) {\n\t\t\tsessionExpiryTimeoutMs =\n\t\t\t\tcreateParams.gcOptions.sessionExpiryTimeoutMs ?? defaultSessionExpiryDurationMs;\n\t\t}\n\t\tsweepTimeoutMs = testOverrideSweepTimeoutMs ?? computeSweepTimeout(sessionExpiryTimeoutMs);\n\n\t\tif (tombstoneGeneration !== undefined || sweepGeneration !== undefined) {\n\t\t\tpersistedGcFeatureMatrix = {\n\t\t\t\ttombstoneGeneration,\n\t\t\t\tsweepGeneration,\n\t\t\t};\n\t\t}\n\t}\n\n\t// Is sweepEnabled for this document?\n\tconst sweepEnabled = shouldAllowGcSweep(\n\t\tpersistedGcFeatureMatrix ?? {} /* persistedGenerations */,\n\t\tcreateParams.gcOptions[gcSweepGenerationOptionName] /* currentGeneration */,\n\t);\n\n\t/**\n\t * Whether GC should run or not. The following conditions have to be met to run sweep:\n\t *\n\t * 1. GC should be enabled for this container.\n\t *\n\t * 2. GC should not be disabled via disableGC GC option.\n\t *\n\t * These conditions can be overridden via runGCKey feature flag.\n\t */\n\tconst shouldRunGC =\n\t\tmc.config.getBoolean(runGCKey) ??\n\t\t// GC must be enabled for the document.\n\t\t(gcEnabled &&\n\t\t\t// GC must not be disabled via GC options.\n\t\t\t!createParams.gcOptions.disableGC);\n\n\t/**\n\t * Whether sweep should run or not. The following conditions have to be met to run sweep:\n\t *\n\t * 1. Overall GC or mark phase must be enabled (this.configs.shouldRunGC).\n\t * 2. Sweep timeout should be available. Without this, we wouldn't know when an object should be deleted.\n\t * 3. The driver must implement the policy limiting the age of snapshots used for loading. Otherwise\n\t * the Sweep Timeout calculation is not valid. We use the persisted value to ensure consistency over time.\n\t * 4. Sweep should be enabled for this container. This can be overridden via runSweep\n\t * feature flag.\n\t */\n\tconst shouldRunSweep =\n\t\tshouldRunGC &&\n\t\tsweepTimeoutMs !== undefined &&\n\t\t(mc.config.getBoolean(runSweepKey) ?? sweepEnabled);\n\n\t// Override inactive timeout if test config or gc options to override it is set.\n\tconst inactiveTimeoutMs =\n\t\tmc.config.getNumber(\"Fluid.GarbageCollection.TestOverride.InactiveTimeoutMs\") ??\n\t\tcreateParams.gcOptions.inactiveTimeoutMs ??\n\t\tdefaultInactiveTimeoutMs;\n\n\t// Inactive timeout must be greater than sweep timeout since a node goes from active -> inactive -> sweep ready.\n\tif (sweepTimeoutMs !== undefined && inactiveTimeoutMs > sweepTimeoutMs) {\n\t\tthrow new UsageError(\"inactive timeout should not be greater than the sweep timeout\");\n\t}\n\n\t// Whether we are running in test mode. In this mode, unreferenced nodes are immediately deleted.\n\tconst testMode =\n\t\tmc.config.getBoolean(gcTestModeKey) ?? createParams.gcOptions.runGCInTestMode === true;\n\t// Whether we are running in tombstone mode. This is enabled by default if sweep won't run. It can be disabled\n\t// via feature flags.\n\tconst tombstoneMode = !shouldRunSweep && mc.config.getBoolean(disableTombstoneKey) !== true;\n\tconst runFullGC = createParams.gcOptions.runFullGC;\n\n\t// If version upgrade is not enabled, fall back to the stable GC version.\n\tconst gcVersionInEffect =\n\t\tmc.config.getBoolean(gcVersionUpgradeToV2Key) === true ? currentGCVersion : stableGCVersion;\n\n\treturn {\n\t\tgcEnabled,\n\t\tsweepEnabled,\n\t\tshouldRunGC,\n\t\tshouldRunSweep,\n\t\trunFullGC,\n\t\ttestMode,\n\t\ttombstoneMode,\n\t\tsessionExpiryTimeoutMs,\n\t\tsweepTimeoutMs,\n\t\tinactiveTimeoutMs,\n\t\tpersistedGcFeatureMatrix,\n\t\tgcVersionInBaseSnapshot,\n\t\tgcVersionInEffect,\n\t};\n}\n\n/**\n * Sweep timeout is the time after which unreferenced content can be swept.\n * Sweep timeout = session expiry timeout + snapshot cache expiry timeout + one day buffer.\n *\n * The snapshot cache expiry timeout cannot be known precisely but the upper bound is 5 days.\n * The buffer is added to account for any clock skew or other edge cases.\n * We use server timestamps throughout so the skew should be minimal but make it 1 day to be safe.\n */\nfunction computeSweepTimeout(sessionExpiryTimeoutMs: number | undefined): number | undefined {\n\tconst bufferMs = oneDayMs;\n\treturn sessionExpiryTimeoutMs && sessionExpiryTimeoutMs + maxSnapshotCacheExpiryMs + bufferMs;\n}\n"]}
@@ -14,8 +14,21 @@ export declare type GCVersion = number;
14
14
  export declare const stableGCVersion: GCVersion;
15
15
  /** The current version of garbage collection. */
16
16
  export declare const currentGCVersion: GCVersion;
17
- /** This undocumented GC Option (on ContainerRuntime Options) allows an app to disable enforcing GC on old documents by incrementing this value */
17
+ /**
18
+ * This undocumented GC Option (on ContainerRuntime Options) allows an app to disable enforcing GC on old documents by incrementing this value
19
+ *
20
+ * If unset, GC Tombstone phase will operate as otherwise configured
21
+ * Otherwise, only enforce GC Tombstone if the passed in value matches the persisted value
22
+ */
18
23
  export declare const gcTombstoneGenerationOptionName = "gcTombstoneGeneration";
24
+ /**
25
+ * This GC Option (on ContainerRuntime Options) allows an app to disable GC Sweep on old documents by incrementing this value.
26
+ *
27
+ * If unset altogether, Sweep will be disabled.
28
+ * If 0 is passed in, Sweep will be enabled for any document with gcSweepGeneration OR gcTombstoneGeneration as 0.
29
+ * If any other number is passed in, Sweep will be enabled only for documents with the same value persisted.
30
+ */
31
+ export declare const gcSweepGenerationOptionName = "gcSweepGeneration";
19
32
  export declare const runGCKey = "Fluid.GarbageCollection.RunGC";
20
33
  export declare const runSweepKey = "Fluid.GarbageCollection.RunSweep";
21
34
  export declare const gcTestModeKey = "Fluid.GarbageCollection.GCTestMode";
@@ -41,10 +54,16 @@ export declare const defaultSessionExpiryDurationMs: number;
41
54
  export interface GCFeatureMatrix {
42
55
  /**
43
56
  * The Tombstone Generation value in effect when this file was created.
44
- * Gives a way for an app to disqualify old files from GC Tombstone enforcement
45
- * Provided via Container Runtime Options
57
+ * Gives a way for an app to disqualify old files from GC Tombstone enforcement.
58
+ * Provided via Container Runtime Options.
46
59
  */
47
60
  tombstoneGeneration?: number;
61
+ /**
62
+ * The Sweep Generation value in effect when this file was created.
63
+ * Gives a way for an app to disqualify old files from GC Sweep.
64
+ * Provided via Container Runtime Options.
65
+ */
66
+ sweepGeneration?: number;
48
67
  }
49
68
  export interface IGCMetadata {
50
69
  /**
@@ -68,6 +87,8 @@ export interface IGCMetadata {
68
87
  */
69
88
  readonly gcFeatureMatrix?: GCFeatureMatrix;
70
89
  /**
90
+ * @deprecated - @see GCFeatureMatrix.sweepGeneration
91
+ *
71
92
  * Tells whether the GC sweep phase is enabled for this container.
72
93
  * - True means sweep phase is enabled.
73
94
  * - False means sweep phase is disabled. If GC is disabled as per gcFeature, sweep is also disabled.
@@ -197,6 +218,8 @@ export interface IGCRuntimeOptions {
197
218
  */
198
219
  gcAllowed?: boolean;
199
220
  /**
221
+ * @deprecated - @see gcSweepGenerationOptionName and @see GCFeatureMatrix.sweepGeneration
222
+ *
200
223
  * Flag that if true, enables GC's sweep phase for a new container.
201
224
  *
202
225
  * This will allow GC to eventually delete unreferenced objects from the container.
@@ -273,6 +296,8 @@ export interface IGarbageCollectorConfigs {
273
296
  readonly persistedGcFeatureMatrix: GCFeatureMatrix | undefined;
274
297
  /** The version of GC in the base snapshot. */
275
298
  readonly gcVersionInBaseSnapshot: GCVersion | undefined;
299
+ /** The current version of GC data in the running code */
300
+ readonly gcVersionInEffect: GCVersion;
276
301
  }
277
302
  /** The state of node that is unreferenced. */
278
303
  export declare const UnreferencedState: {
@@ -1 +1 @@
1
- {"version":3,"file":"gcDefinitions.d.ts","sourceRoot":"","sources":["../../src/gc/gcDefinitions.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"gcDefinitions.d.ts","sourceRoot":"","sources":["../../src/gc/gcDefinitions.ts"],"names":[],"mappings":"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"}
@@ -6,8 +6,21 @@
6
6
  export const stableGCVersion = 1;
7
7
  /** The current version of garbage collection. */
8
8
  export const currentGCVersion = 2;
9
- /** This undocumented GC Option (on ContainerRuntime Options) allows an app to disable enforcing GC on old documents by incrementing this value */
9
+ /**
10
+ * This undocumented GC Option (on ContainerRuntime Options) allows an app to disable enforcing GC on old documents by incrementing this value
11
+ *
12
+ * If unset, GC Tombstone phase will operate as otherwise configured
13
+ * Otherwise, only enforce GC Tombstone if the passed in value matches the persisted value
14
+ */
10
15
  export const gcTombstoneGenerationOptionName = "gcTombstoneGeneration";
16
+ /**
17
+ * This GC Option (on ContainerRuntime Options) allows an app to disable GC Sweep on old documents by incrementing this value.
18
+ *
19
+ * If unset altogether, Sweep will be disabled.
20
+ * If 0 is passed in, Sweep will be enabled for any document with gcSweepGeneration OR gcTombstoneGeneration as 0.
21
+ * If any other number is passed in, Sweep will be enabled only for documents with the same value persisted.
22
+ */
23
+ export const gcSweepGenerationOptionName = "gcSweepGeneration";
11
24
  // Feature gate key to turn GC on / off.
12
25
  export const runGCKey = "Fluid.GarbageCollection.RunGC";
13
26
  // Feature gate key to turn GC sweep on / off.
@@ -1 +1 @@
1
- {"version":3,"file":"gcDefinitions.js","sourceRoot":"","sources":["../../src/gc/gcDefinitions.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAiBH,8DAA8D;AAC9D,MAAM,CAAC,MAAM,eAAe,GAAc,CAAC,CAAC;AAC5C,iDAAiD;AACjD,MAAM,CAAC,MAAM,gBAAgB,GAAc,CAAC,CAAC;AAE7C,kJAAkJ;AAClJ,MAAM,CAAC,MAAM,+BAA+B,GAAG,uBAAuB,CAAC;AAEvE,wCAAwC;AACxC,MAAM,CAAC,MAAM,QAAQ,GAAG,+BAA+B,CAAC;AACxD,8CAA8C;AAC9C,MAAM,CAAC,MAAM,WAAW,GAAG,kCAAkC,CAAC;AAC9D,kDAAkD;AAClD,MAAM,CAAC,MAAM,aAAa,GAAG,oCAAoC,CAAC;AAClE,mEAAmE;AACnE,MAAM,CAAC,MAAM,mBAAmB,GAAG,0CAA0C,CAAC;AAC9E,6CAA6C;AAC7C,MAAM,CAAC,MAAM,kBAAkB,GAAG,yCAAyC,CAAC;AAC5E,qHAAqH;AACrH,MAAM,CAAC,MAAM,mBAAmB,GAAG,0CAA0C,CAAC;AAC9E,wFAAwF;AACxF,MAAM,CAAC,MAAM,uBAAuB,GAAG,8CAA8C,CAAC;AACtF,0GAA0G;AAC1G,MAAM,CAAC,MAAM,wBAAwB,GAAG,+CAA+C,CAAC;AACxF,6CAA6C;AAC7C,MAAM,CAAC,MAAM,uBAAuB,GAAG,8CAA8C,CAAC;AACtF,kDAAkD;AAClD,yEAAyE;AACzE,MAAM,CAAC,MAAM,kBAAkB,GAAG,8CAA8C,CAAC;AACjF,wDAAwD;AACxD,MAAM,CAAC,MAAM,uBAAuB,GAAG,mDAAmD,CAAC;AAE3F,2BAA2B;AAC3B,MAAM,CAAC,MAAM,QAAQ,GAAG,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,IAAI,CAAC;AAEhD;;;;;GAKG;AACH,MAAM,CAAC,MAAM,wBAAwB,GAAG,CAAC,GAAG,QAAQ,CAAC;AAErD,MAAM,CAAC,MAAM,wBAAwB,GAAG,CAAC,GAAG,QAAQ,CAAC,CAAC,SAAS;AAC/D,MAAM,CAAC,MAAM,8BAA8B,GAAG,EAAE,GAAG,QAAQ,CAAC,CAAC,UAAU;AAoEvE,uDAAuD;AACvD,MAAM,CAAC,MAAM,UAAU,GAAG;IACzB,kCAAkC;IAClC,SAAS,EAAE,WAAW;IACtB,8DAA8D;IAC9D,YAAY,EAAE,cAAc;IAC5B,6EAA6E;IAC7E,IAAI,EAAE,MAAM;IACZ,+DAA+D;IAC/D,KAAK,EAAE,OAAO;CACd,CAAC;AAsMF,8CAA8C;AAC9C,MAAM,CAAC,MAAM,iBAAiB,GAAG;IAChC,gEAAgE;IAChE,MAAM,EAAE,QAAQ;IAChB,mEAAmE;IACnE,QAAQ,EAAE,UAAU;IACpB,0DAA0D;IAC1D,UAAU,EAAE,YAAY;CACf,CAAC","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n */\n\nimport { ICriticalContainerError } from \"@fluidframework/container-definitions\";\nimport { IRequestHeader } from \"@fluidframework/core-interfaces\";\nimport { ISnapshotTree } from \"@fluidframework/protocol-definitions\";\nimport {\n\tIGarbageCollectionData,\n\tIGarbageCollectionDetailsBase,\n\tISummarizeResult,\n\tITelemetryContext,\n} from \"@fluidframework/runtime-definitions\";\nimport { ReadAndParseBlob, RefreshSummaryResult } from \"@fluidframework/runtime-utils\";\nimport { ITelemetryLogger } from \"@fluidframework/common-definitions\";\nimport { IContainerRuntimeMetadata, ICreateContainerMetadata } from \"../summary\";\n\nexport type GCVersion = number;\n\n/** The stable version of garbage collection in production. */\nexport const stableGCVersion: GCVersion = 1;\n/** The current version of garbage collection. */\nexport const currentGCVersion: GCVersion = 2;\n\n/** This undocumented GC Option (on ContainerRuntime Options) allows an app to disable enforcing GC on old documents by incrementing this value */\nexport const gcTombstoneGenerationOptionName = \"gcTombstoneGeneration\";\n\n// Feature gate key to turn GC on / off.\nexport const runGCKey = \"Fluid.GarbageCollection.RunGC\";\n// Feature gate key to turn GC sweep on / off.\nexport const runSweepKey = \"Fluid.GarbageCollection.RunSweep\";\n// Feature gate key to turn GC test mode on / off.\nexport const gcTestModeKey = \"Fluid.GarbageCollection.GCTestMode\";\n// Feature gate key to expire a session after a set period of time.\nexport const runSessionExpiryKey = \"Fluid.GarbageCollection.RunSessionExpiry\";\n// Feature gate key to turn GC sweep log off.\nexport const disableSweepLogKey = \"Fluid.GarbageCollection.DisableSweepLog\";\n// Feature gate key to disable the tombstone feature, i.e., tombstone information is not read / written into summary.\nexport const disableTombstoneKey = \"Fluid.GarbageCollection.DisableTombstone\";\n// Feature gate to enable throwing an error when tombstone object is loaded (requested).\nexport const throwOnTombstoneLoadKey = \"Fluid.GarbageCollection.ThrowOnTombstoneLoad\";\n// Feature gate to enable throwing an error when tombstone object is used (e.g. outgoing or incoming ops).\nexport const throwOnTombstoneUsageKey = \"Fluid.GarbageCollection.ThrowOnTombstoneUsage\";\n// Feature gate to enable GC version upgrade.\nexport const gcVersionUpgradeToV2Key = \"Fluid.GarbageCollection.GCVersionUpgradeToV2\";\n// Feature gate to enable GC sweep for datastores.\n// TODO: Remove Test from the flag when we are confident to turn on sweep\nexport const sweepDatastoresKey = \"Fluid.GarbageCollection.Test.SweepDataStores\";\n// Feature gate to enable GC sweep for attachment blobs.\nexport const sweepAttachmentBlobsKey = \"Fluid.GarbageCollection.Test.SweepAttachmentBlobs\";\n\n// One day in milliseconds.\nexport const oneDayMs = 1 * 24 * 60 * 60 * 1000;\n\n/**\n * The maximum snapshot cache expiry in the driver. This is used to calculate the sweep timeout.\n * Sweep timeout = session expiry timeout + snapshot cache expiry timeout + a buffer.\n * The snapshot cache expiry timeout cannot be known precisely but the upper bound is 5 days, i.e., any snapshot\n * in cache will be invalidated before 5 days.\n */\nexport const maxSnapshotCacheExpiryMs = 5 * oneDayMs;\n\nexport const defaultInactiveTimeoutMs = 7 * oneDayMs; // 7 days\nexport const defaultSessionExpiryDurationMs = 30 * oneDayMs; // 30 days\n\n/** @see IGCMetadata.gcFeatureMatrix */\nexport interface GCFeatureMatrix {\n\t/**\n\t * The Tombstone Generation value in effect when this file was created.\n\t * Gives a way for an app to disqualify old files from GC Tombstone enforcement\n\t * Provided via Container Runtime Options\n\t */\n\ttombstoneGeneration?: number;\n}\n\nexport interface IGCMetadata {\n\t/**\n\t * The version of the GC code that was run to generate the GC data that is written in the summary.\n\t * If the persisted value doesn't match the current value in the code, saved GC data will be discarded and regenerated from scratch.\n\t * Also, used to determine whether GC is enabled for this container or not:\n\t * - A value of 0 or undefined means GC is disabled.\n\t * - A value greater than 0 means GC is enabled.\n\t */\n\treadonly gcFeature?: GCVersion;\n\n\t/**\n\t * A collection of different numerical \"Generations\" for different features,\n\t * used to determine feature availability over time.\n\t * This info may come from multiple sources (FF code, config service, app via Container Runtime Options),\n\t * and pertains to aspects of the document that may be fixed for its lifetime.\n\t *\n\t * For each dimension, if the persisted value doesn't match the currently provided value,\n\t * then this file does not support the corresponding feature as currently implemented.\n\t *\n\t * Guidance is that if no value is provided at runtime, it should result in the current default behavior.\n\t */\n\treadonly gcFeatureMatrix?: GCFeatureMatrix;\n\t/**\n\t * Tells whether the GC sweep phase is enabled for this container.\n\t * - True means sweep phase is enabled.\n\t * - False means sweep phase is disabled. If GC is disabled as per gcFeature, sweep is also disabled.\n\t */\n\treadonly sweepEnabled?: boolean;\n\t/** If this is present, the session for this container will expire after this time and the container will close */\n\treadonly sessionExpiryTimeoutMs?: number;\n\t/** How long to wait after an object is unreferenced before deleting it via GC Sweep */\n\treadonly sweepTimeoutMs?: number;\n}\n\n/** The statistics of the system state after a garbage collection run. */\nexport interface IGCStats {\n\t/** The number of nodes in the container. */\n\tnodeCount: number;\n\t/** The number of data stores in the container. */\n\tdataStoreCount: number;\n\t/** The number of attachment blobs in the container. */\n\tattachmentBlobCount: number;\n\t/** The number of unreferenced nodes in the container. */\n\tunrefNodeCount: number;\n\t/** The number of unreferenced data stores in the container. */\n\tunrefDataStoreCount: number;\n\t/** The number of unreferenced attachment blobs in the container. */\n\tunrefAttachmentBlobCount: number;\n\t/** The number of nodes whose reference state updated since last GC run. */\n\tupdatedNodeCount: number;\n\t/** The number of data stores whose reference state updated since last GC run. */\n\tupdatedDataStoreCount: number;\n\t/** The number of attachment blobs whose reference state updated since last GC run. */\n\tupdatedAttachmentBlobCount: number;\n}\n\n/** The types of GC nodes in the GC reference graph. */\nexport const GCNodeType = {\n\t// Nodes that are for data stores.\n\tDataStore: \"DataStore\",\n\t// Nodes that are within a data store. For example, DDS nodes.\n\tSubDataStore: \"SubDataStore\",\n\t// Nodes that are for attachment blobs, i.e., blobs uploaded via BlobManager.\n\tBlob: \"Blob\",\n\t// Nodes that are neither of the above. For example, root node.\n\tOther: \"Other\",\n};\nexport type GCNodeType = typeof GCNodeType[keyof typeof GCNodeType];\n\n// NOTE: Once this is removed from the package exports in the next major, the deprecation tag can be removed as well\n/**\n * @deprecated - Was only to be used internally anyway, no replacement provided.\n * Defines the APIs for the runtime object to be passed to the garbage collector.\n */\nexport interface IGarbageCollectionRuntime {\n\t/** Before GC runs, called to notify the runtime to update any pending GC state. */\n\tupdateStateBeforeGC(): Promise<void>;\n\t/** Returns the garbage collection data of the runtime. */\n\tgetGCData(fullGC?: boolean): Promise<IGarbageCollectionData>;\n\t/** After GC has run, called to notify the runtime of routes that are used in it. */\n\tupdateUsedRoutes(usedRoutes: string[]): void;\n\t/** After GC has run, called to notify the runtime of routes that are unused in it. */\n\tupdateUnusedRoutes(unusedRoutes: string[]): void;\n\t/**\n\t * After GC has run and identified nodes that are sweep ready, called to delete the sweep ready nodes. The runtime\n\t * should return the routes of nodes that were deleted.\n\t * @param sweepReadyRoutes - The routes of nodes that are sweep ready and should be deleted.\n\t */\n\tdeleteSweepReadyNodes(sweepReadyRoutes: string[]): string[];\n\t/** Called to notify the runtime of routes that are tombstones. */\n\tupdateTombstonedRoutes(tombstoneRoutes: string[]): void;\n\t/** Returns a referenced timestamp to be used to track unreferenced nodes. */\n\tgetCurrentReferenceTimestampMs(): number | undefined;\n\t/** Returns the type of the GC node. */\n\tgetNodeType(nodePath: string): GCNodeType;\n\t/** Called when the runtime should close because of an error. */\n\tcloseFn: (error?: ICriticalContainerError) => void;\n\t/** If false, loading or using a Tombstoned object should merely log, not fail */\n\tgcTombstoneEnforcementAllowed: boolean;\n}\n\n/** Defines the contract for the garbage collector. */\nexport interface IGarbageCollector {\n\t/** Tells whether GC should run or not. */\n\treadonly shouldRunGC: boolean;\n\t/** Tells whether the GC state in summary needs to be reset in the next summary. */\n\treadonly summaryStateNeedsReset: boolean;\n\t/** Initialize the state from the base snapshot after its creation. */\n\tinitializeBaseState(): Promise<void>;\n\t/** Run garbage collection and update the reference / used state of the system. */\n\tcollectGarbage(\n\t\toptions: {\n\t\t\tlogger?: ITelemetryLogger;\n\t\t\trunSweep?: boolean;\n\t\t\tfullGC?: boolean;\n\t\t},\n\t\ttelemetryContext?: ITelemetryContext,\n\t): Promise<IGCStats | undefined>;\n\t/** Summarizes the GC data and returns it as a summary tree. */\n\tsummarize(\n\t\tfullTree: boolean,\n\t\ttrackState: boolean,\n\t\ttelemetryContext?: ITelemetryContext,\n\t): ISummarizeResult | undefined;\n\t/** Returns the garbage collector specific metadata to be written into the summary. */\n\tgetMetadata(): IGCMetadata;\n\t/** Returns the GC details generated from the base snapshot. */\n\tgetBaseGCDetails(): Promise<IGarbageCollectionDetailsBase>;\n\t/** Called when the latest summary of the system has been refreshed. */\n\trefreshLatestSummary(\n\t\tproposalHandle: string | undefined,\n\t\tresult: RefreshSummaryResult,\n\t\treadAndParseBlob: ReadAndParseBlob,\n\t): Promise<void>;\n\t/** Called when a node is updated. Used to detect and log when an inactive node is changed or loaded. */\n\tnodeUpdated(\n\t\tnodePath: string,\n\t\treason: \"Loaded\" | \"Changed\",\n\t\ttimestampMs?: number,\n\t\tpackagePath?: readonly string[],\n\t\trequestHeaders?: IRequestHeader,\n\t): void;\n\t/** Called when a reference is added to a node. Used to identify nodes that were referenced between summaries. */\n\taddedOutboundReference(fromNodePath: string, toNodePath: string): void;\n\t/** Returns true if this node has been deleted by GC during sweep phase. */\n\tisNodeDeleted(nodePath: string): boolean;\n\tsetConnectionState(connected: boolean, clientId?: string): void;\n\tdispose(): void;\n}\n\n/** Parameters necessary for creating a GarbageCollector. */\nexport interface IGarbageCollectorCreateParams {\n\treadonly runtime: IGarbageCollectionRuntime;\n\treadonly gcOptions: IGCRuntimeOptions;\n\treadonly baseLogger: ITelemetryLogger;\n\treadonly existing: boolean;\n\treadonly metadata: IContainerRuntimeMetadata | undefined;\n\treadonly createContainerMetadata: ICreateContainerMetadata;\n\treadonly baseSnapshot: ISnapshotTree | undefined;\n\treadonly isSummarizerClient: boolean;\n\treadonly getNodePackagePath: (nodePath: string) => Promise<readonly string[] | undefined>;\n\treadonly getLastSummaryTimestampMs: () => number | undefined;\n\treadonly readAndParseBlob: ReadAndParseBlob;\n\treadonly activeConnection: () => boolean;\n\treadonly getContainerDiagnosticId: () => string;\n}\n\nexport interface IGCRuntimeOptions {\n\t/**\n\t * Flag that if true, will enable running garbage collection (GC) for a new container.\n\t *\n\t * GC has mark phase and sweep phase. In mark phase, unreferenced objects are identified\n\t * and marked as such in the summary. This option enables the mark phase.\n\t * In sweep phase, unreferenced objects are eventually deleted from the container if they meet certain conditions.\n\t * Sweep phase can be enabled via the \"sweepAllowed\" option.\n\t *\n\t * Note: This setting is persisted in the container's summary and cannot be changed.\n\t */\n\tgcAllowed?: boolean;\n\n\t/**\n\t * Flag that if true, enables GC's sweep phase for a new container.\n\t *\n\t * This will allow GC to eventually delete unreferenced objects from the container.\n\t * This flag should only be set to true if \"gcAllowed\" is true.\n\t *\n\t * Note: This setting is persisted in the container's summary and cannot be changed.\n\t */\n\tsweepAllowed?: boolean;\n\n\t/**\n\t * Flag that if true, will disable garbage collection for the session.\n\t * Can be used to disable running GC on containers where it is allowed via the gcAllowed option.\n\t */\n\tdisableGC?: boolean;\n\n\t/**\n\t * Flag that will bypass optimizations and generate GC data for all nodes irrespective of whether a node\n\t * changed or not.\n\t */\n\trunFullGC?: boolean;\n\n\t/**\n\t * Maximum session duration for a new container. If not present, a default value will be used.\n\t *\n\t * Note: This setting is persisted in the container's summary and cannot be changed.\n\t */\n\tsessionExpiryTimeoutMs?: number;\n\n\t/**\n\t * Allows additional GC options to be passed.\n\t */\n\t[key: string]: any;\n}\n\n/**\n * The configurations for Garbage Collector that determines what runs and how.\n */\nexport interface IGarbageCollectorConfigs {\n\t/**\n\t * Tracks if GC is enabled for this document. This is specified during document creation and doesn't change\n\t * throughout its lifetime.\n\t */\n\treadonly gcEnabled: boolean;\n\t/**\n\t * Tracks if sweep phase is enabled for this document. This is specified during document creation and doesn't change\n\t * throughout its lifetime.\n\t */\n\treadonly sweepEnabled: boolean;\n\t/**\n\t * Tracks if GC should run or not. Even if GC is enabled for a document (see gcEnabled), it can be explicitly\n\t * disabled via runtime options or feature flags.\n\t */\n\treadonly shouldRunGC: boolean;\n\t/**\n\t * Tracks if sweep phase should run or not. Even if the sweep phase is enabled for a document (see sweepEnabled), it\n\t * can be explicitly disabled via feature flags. It also won't run if session expiry is not enabled.\n\t */\n\treadonly shouldRunSweep: boolean;\n\t/**\n\t * If true, bypass optimizations and generate GC data for all nodes irrespective of whether a node changed or not.\n\t */\n\treadonly runFullGC: boolean | undefined;\n\t/** The time in ms to expire a session for a client for gc. */\n\treadonly sessionExpiryTimeoutMs: number | undefined;\n\t/** The time after which an unreferenced node is ready to be swept. */\n\treadonly sweepTimeoutMs: number | undefined;\n\t/** The time after which an unreferenced node is inactive. */\n\treadonly inactiveTimeoutMs: number;\n\t/** Tracks whether GC should run in test mode. In this mode, unreferenced objects are deleted immediately. */\n\treadonly testMode: boolean;\n\t/**\n\t * Tracks whether GC should run in tombstone mode. In this mode, sweep ready objects are marked as tombstones.\n\t * In interactive (non-summarizer) clients, tombstone objects behave as if they are deleted, i.e., access to them\n\t * is not allowed. However, these objects can be accessed after referencing them first. It is used as a staging\n\t * step for sweep where accidental sweep ready objects can be recovered.\n\t */\n\treadonly tombstoneMode: boolean;\n\t/** @see GCFeatureMatrix. */\n\treadonly persistedGcFeatureMatrix: GCFeatureMatrix | undefined;\n\t/** The version of GC in the base snapshot. */\n\treadonly gcVersionInBaseSnapshot: GCVersion | undefined;\n}\n\n/** The state of node that is unreferenced. */\nexport const UnreferencedState = {\n\t/** The node is active, i.e., it can become referenced again. */\n\tActive: \"Active\",\n\t/** The node is inactive, i.e., it should not become referenced. */\n\tInactive: \"Inactive\",\n\t/** The node is ready to be deleted by the sweep phase. */\n\tSweepReady: \"SweepReady\",\n} as const;\nexport type UnreferencedState = typeof UnreferencedState[keyof typeof UnreferencedState];\n"]}
1
+ {"version":3,"file":"gcDefinitions.js","sourceRoot":"","sources":["../../src/gc/gcDefinitions.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAiBH,8DAA8D;AAC9D,MAAM,CAAC,MAAM,eAAe,GAAc,CAAC,CAAC;AAC5C,iDAAiD;AACjD,MAAM,CAAC,MAAM,gBAAgB,GAAc,CAAC,CAAC;AAE7C;;;;;GAKG;AACH,MAAM,CAAC,MAAM,+BAA+B,GAAG,uBAAuB,CAAC;AACvE;;;;;;GAMG;AACH,MAAM,CAAC,MAAM,2BAA2B,GAAG,mBAAmB,CAAC;AAE/D,wCAAwC;AACxC,MAAM,CAAC,MAAM,QAAQ,GAAG,+BAA+B,CAAC;AACxD,8CAA8C;AAC9C,MAAM,CAAC,MAAM,WAAW,GAAG,kCAAkC,CAAC;AAC9D,kDAAkD;AAClD,MAAM,CAAC,MAAM,aAAa,GAAG,oCAAoC,CAAC;AAClE,mEAAmE;AACnE,MAAM,CAAC,MAAM,mBAAmB,GAAG,0CAA0C,CAAC;AAC9E,6CAA6C;AAC7C,MAAM,CAAC,MAAM,kBAAkB,GAAG,yCAAyC,CAAC;AAC5E,qHAAqH;AACrH,MAAM,CAAC,MAAM,mBAAmB,GAAG,0CAA0C,CAAC;AAC9E,wFAAwF;AACxF,MAAM,CAAC,MAAM,uBAAuB,GAAG,8CAA8C,CAAC;AACtF,0GAA0G;AAC1G,MAAM,CAAC,MAAM,wBAAwB,GAAG,+CAA+C,CAAC;AACxF,6CAA6C;AAC7C,MAAM,CAAC,MAAM,uBAAuB,GAAG,8CAA8C,CAAC;AACtF,kDAAkD;AAClD,yEAAyE;AACzE,MAAM,CAAC,MAAM,kBAAkB,GAAG,8CAA8C,CAAC;AACjF,wDAAwD;AACxD,MAAM,CAAC,MAAM,uBAAuB,GAAG,mDAAmD,CAAC;AAE3F,2BAA2B;AAC3B,MAAM,CAAC,MAAM,QAAQ,GAAG,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,IAAI,CAAC;AAEhD;;;;;GAKG;AACH,MAAM,CAAC,MAAM,wBAAwB,GAAG,CAAC,GAAG,QAAQ,CAAC;AAErD,MAAM,CAAC,MAAM,wBAAwB,GAAG,CAAC,GAAG,QAAQ,CAAC,CAAC,SAAS;AAC/D,MAAM,CAAC,MAAM,8BAA8B,GAAG,EAAE,GAAG,QAAQ,CAAC,CAAC,UAAU;AA4EvE,uDAAuD;AACvD,MAAM,CAAC,MAAM,UAAU,GAAG;IACzB,kCAAkC;IAClC,SAAS,EAAE,WAAW;IACtB,8DAA8D;IAC9D,YAAY,EAAE,cAAc;IAC5B,6EAA6E;IAC7E,IAAI,EAAE,MAAM;IACZ,+DAA+D;IAC/D,KAAK,EAAE,OAAO;CACd,CAAC;AA0MF,8CAA8C;AAC9C,MAAM,CAAC,MAAM,iBAAiB,GAAG;IAChC,gEAAgE;IAChE,MAAM,EAAE,QAAQ;IAChB,mEAAmE;IACnE,QAAQ,EAAE,UAAU;IACpB,0DAA0D;IAC1D,UAAU,EAAE,YAAY;CACf,CAAC","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n */\n\nimport { ICriticalContainerError } from \"@fluidframework/container-definitions\";\nimport { IRequestHeader } from \"@fluidframework/core-interfaces\";\nimport { ISnapshotTree } from \"@fluidframework/protocol-definitions\";\nimport {\n\tIGarbageCollectionData,\n\tIGarbageCollectionDetailsBase,\n\tISummarizeResult,\n\tITelemetryContext,\n} from \"@fluidframework/runtime-definitions\";\nimport { ReadAndParseBlob, RefreshSummaryResult } from \"@fluidframework/runtime-utils\";\nimport { ITelemetryLogger } from \"@fluidframework/common-definitions\";\nimport { IContainerRuntimeMetadata, ICreateContainerMetadata } from \"../summary\";\n\nexport type GCVersion = number;\n\n/** The stable version of garbage collection in production. */\nexport const stableGCVersion: GCVersion = 1;\n/** The current version of garbage collection. */\nexport const currentGCVersion: GCVersion = 2;\n\n/**\n * This undocumented GC Option (on ContainerRuntime Options) allows an app to disable enforcing GC on old documents by incrementing this value\n *\n * If unset, GC Tombstone phase will operate as otherwise configured\n * Otherwise, only enforce GC Tombstone if the passed in value matches the persisted value\n */\nexport const gcTombstoneGenerationOptionName = \"gcTombstoneGeneration\";\n/**\n * This GC Option (on ContainerRuntime Options) allows an app to disable GC Sweep on old documents by incrementing this value.\n *\n * If unset altogether, Sweep will be disabled.\n * If 0 is passed in, Sweep will be enabled for any document with gcSweepGeneration OR gcTombstoneGeneration as 0.\n * If any other number is passed in, Sweep will be enabled only for documents with the same value persisted.\n */\nexport const gcSweepGenerationOptionName = \"gcSweepGeneration\";\n\n// Feature gate key to turn GC on / off.\nexport const runGCKey = \"Fluid.GarbageCollection.RunGC\";\n// Feature gate key to turn GC sweep on / off.\nexport const runSweepKey = \"Fluid.GarbageCollection.RunSweep\";\n// Feature gate key to turn GC test mode on / off.\nexport const gcTestModeKey = \"Fluid.GarbageCollection.GCTestMode\";\n// Feature gate key to expire a session after a set period of time.\nexport const runSessionExpiryKey = \"Fluid.GarbageCollection.RunSessionExpiry\";\n// Feature gate key to turn GC sweep log off.\nexport const disableSweepLogKey = \"Fluid.GarbageCollection.DisableSweepLog\";\n// Feature gate key to disable the tombstone feature, i.e., tombstone information is not read / written into summary.\nexport const disableTombstoneKey = \"Fluid.GarbageCollection.DisableTombstone\";\n// Feature gate to enable throwing an error when tombstone object is loaded (requested).\nexport const throwOnTombstoneLoadKey = \"Fluid.GarbageCollection.ThrowOnTombstoneLoad\";\n// Feature gate to enable throwing an error when tombstone object is used (e.g. outgoing or incoming ops).\nexport const throwOnTombstoneUsageKey = \"Fluid.GarbageCollection.ThrowOnTombstoneUsage\";\n// Feature gate to enable GC version upgrade.\nexport const gcVersionUpgradeToV2Key = \"Fluid.GarbageCollection.GCVersionUpgradeToV2\";\n// Feature gate to enable GC sweep for datastores.\n// TODO: Remove Test from the flag when we are confident to turn on sweep\nexport const sweepDatastoresKey = \"Fluid.GarbageCollection.Test.SweepDataStores\";\n// Feature gate to enable GC sweep for attachment blobs.\nexport const sweepAttachmentBlobsKey = \"Fluid.GarbageCollection.Test.SweepAttachmentBlobs\";\n\n// One day in milliseconds.\nexport const oneDayMs = 1 * 24 * 60 * 60 * 1000;\n\n/**\n * The maximum snapshot cache expiry in the driver. This is used to calculate the sweep timeout.\n * Sweep timeout = session expiry timeout + snapshot cache expiry timeout + a buffer.\n * The snapshot cache expiry timeout cannot be known precisely but the upper bound is 5 days, i.e., any snapshot\n * in cache will be invalidated before 5 days.\n */\nexport const maxSnapshotCacheExpiryMs = 5 * oneDayMs;\n\nexport const defaultInactiveTimeoutMs = 7 * oneDayMs; // 7 days\nexport const defaultSessionExpiryDurationMs = 30 * oneDayMs; // 30 days\n\n/** @see IGCMetadata.gcFeatureMatrix */\nexport interface GCFeatureMatrix {\n\t/**\n\t * The Tombstone Generation value in effect when this file was created.\n\t * Gives a way for an app to disqualify old files from GC Tombstone enforcement.\n\t * Provided via Container Runtime Options.\n\t */\n\ttombstoneGeneration?: number;\n\t/**\n\t * The Sweep Generation value in effect when this file was created.\n\t * Gives a way for an app to disqualify old files from GC Sweep.\n\t * Provided via Container Runtime Options.\n\t */\n\tsweepGeneration?: number;\n}\n\nexport interface IGCMetadata {\n\t/**\n\t * The version of the GC code that was run to generate the GC data that is written in the summary.\n\t * If the persisted value doesn't match the current value in the code, saved GC data will be discarded and regenerated from scratch.\n\t * Also, used to determine whether GC is enabled for this container or not:\n\t * - A value of 0 or undefined means GC is disabled.\n\t * - A value greater than 0 means GC is enabled.\n\t */\n\treadonly gcFeature?: GCVersion;\n\n\t/**\n\t * A collection of different numerical \"Generations\" for different features,\n\t * used to determine feature availability over time.\n\t * This info may come from multiple sources (FF code, config service, app via Container Runtime Options),\n\t * and pertains to aspects of the document that may be fixed for its lifetime.\n\t *\n\t * For each dimension, if the persisted value doesn't match the currently provided value,\n\t * then this file does not support the corresponding feature as currently implemented.\n\t *\n\t * Guidance is that if no value is provided at runtime, it should result in the current default behavior.\n\t */\n\treadonly gcFeatureMatrix?: GCFeatureMatrix;\n\t/**\n\t * @deprecated - @see GCFeatureMatrix.sweepGeneration\n\t *\n\t * Tells whether the GC sweep phase is enabled for this container.\n\t * - True means sweep phase is enabled.\n\t * - False means sweep phase is disabled. If GC is disabled as per gcFeature, sweep is also disabled.\n\t */\n\treadonly sweepEnabled?: boolean;\n\t/** If this is present, the session for this container will expire after this time and the container will close */\n\treadonly sessionExpiryTimeoutMs?: number;\n\t/** How long to wait after an object is unreferenced before deleting it via GC Sweep */\n\treadonly sweepTimeoutMs?: number;\n}\n\n/** The statistics of the system state after a garbage collection run. */\nexport interface IGCStats {\n\t/** The number of nodes in the container. */\n\tnodeCount: number;\n\t/** The number of data stores in the container. */\n\tdataStoreCount: number;\n\t/** The number of attachment blobs in the container. */\n\tattachmentBlobCount: number;\n\t/** The number of unreferenced nodes in the container. */\n\tunrefNodeCount: number;\n\t/** The number of unreferenced data stores in the container. */\n\tunrefDataStoreCount: number;\n\t/** The number of unreferenced attachment blobs in the container. */\n\tunrefAttachmentBlobCount: number;\n\t/** The number of nodes whose reference state updated since last GC run. */\n\tupdatedNodeCount: number;\n\t/** The number of data stores whose reference state updated since last GC run. */\n\tupdatedDataStoreCount: number;\n\t/** The number of attachment blobs whose reference state updated since last GC run. */\n\tupdatedAttachmentBlobCount: number;\n}\n\n/** The types of GC nodes in the GC reference graph. */\nexport const GCNodeType = {\n\t// Nodes that are for data stores.\n\tDataStore: \"DataStore\",\n\t// Nodes that are within a data store. For example, DDS nodes.\n\tSubDataStore: \"SubDataStore\",\n\t// Nodes that are for attachment blobs, i.e., blobs uploaded via BlobManager.\n\tBlob: \"Blob\",\n\t// Nodes that are neither of the above. For example, root node.\n\tOther: \"Other\",\n};\nexport type GCNodeType = typeof GCNodeType[keyof typeof GCNodeType];\n\n// NOTE: Once this is removed from the package exports in the next major, the deprecation tag can be removed as well\n/**\n * @deprecated - Was only to be used internally anyway, no replacement provided.\n * Defines the APIs for the runtime object to be passed to the garbage collector.\n */\nexport interface IGarbageCollectionRuntime {\n\t/** Before GC runs, called to notify the runtime to update any pending GC state. */\n\tupdateStateBeforeGC(): Promise<void>;\n\t/** Returns the garbage collection data of the runtime. */\n\tgetGCData(fullGC?: boolean): Promise<IGarbageCollectionData>;\n\t/** After GC has run, called to notify the runtime of routes that are used in it. */\n\tupdateUsedRoutes(usedRoutes: string[]): void;\n\t/** After GC has run, called to notify the runtime of routes that are unused in it. */\n\tupdateUnusedRoutes(unusedRoutes: string[]): void;\n\t/**\n\t * After GC has run and identified nodes that are sweep ready, called to delete the sweep ready nodes. The runtime\n\t * should return the routes of nodes that were deleted.\n\t * @param sweepReadyRoutes - The routes of nodes that are sweep ready and should be deleted.\n\t */\n\tdeleteSweepReadyNodes(sweepReadyRoutes: string[]): string[];\n\t/** Called to notify the runtime of routes that are tombstones. */\n\tupdateTombstonedRoutes(tombstoneRoutes: string[]): void;\n\t/** Returns a referenced timestamp to be used to track unreferenced nodes. */\n\tgetCurrentReferenceTimestampMs(): number | undefined;\n\t/** Returns the type of the GC node. */\n\tgetNodeType(nodePath: string): GCNodeType;\n\t/** Called when the runtime should close because of an error. */\n\tcloseFn: (error?: ICriticalContainerError) => void;\n\t/** If false, loading or using a Tombstoned object should merely log, not fail */\n\tgcTombstoneEnforcementAllowed: boolean;\n}\n\n/** Defines the contract for the garbage collector. */\nexport interface IGarbageCollector {\n\t/** Tells whether GC should run or not. */\n\treadonly shouldRunGC: boolean;\n\t/** Tells whether the GC state in summary needs to be reset in the next summary. */\n\treadonly summaryStateNeedsReset: boolean;\n\t/** Initialize the state from the base snapshot after its creation. */\n\tinitializeBaseState(): Promise<void>;\n\t/** Run garbage collection and update the reference / used state of the system. */\n\tcollectGarbage(\n\t\toptions: {\n\t\t\tlogger?: ITelemetryLogger;\n\t\t\trunSweep?: boolean;\n\t\t\tfullGC?: boolean;\n\t\t},\n\t\ttelemetryContext?: ITelemetryContext,\n\t): Promise<IGCStats | undefined>;\n\t/** Summarizes the GC data and returns it as a summary tree. */\n\tsummarize(\n\t\tfullTree: boolean,\n\t\ttrackState: boolean,\n\t\ttelemetryContext?: ITelemetryContext,\n\t): ISummarizeResult | undefined;\n\t/** Returns the garbage collector specific metadata to be written into the summary. */\n\tgetMetadata(): IGCMetadata;\n\t/** Returns the GC details generated from the base snapshot. */\n\tgetBaseGCDetails(): Promise<IGarbageCollectionDetailsBase>;\n\t/** Called when the latest summary of the system has been refreshed. */\n\trefreshLatestSummary(\n\t\tproposalHandle: string | undefined,\n\t\tresult: RefreshSummaryResult,\n\t\treadAndParseBlob: ReadAndParseBlob,\n\t): Promise<void>;\n\t/** Called when a node is updated. Used to detect and log when an inactive node is changed or loaded. */\n\tnodeUpdated(\n\t\tnodePath: string,\n\t\treason: \"Loaded\" | \"Changed\",\n\t\ttimestampMs?: number,\n\t\tpackagePath?: readonly string[],\n\t\trequestHeaders?: IRequestHeader,\n\t): void;\n\t/** Called when a reference is added to a node. Used to identify nodes that were referenced between summaries. */\n\taddedOutboundReference(fromNodePath: string, toNodePath: string): void;\n\t/** Returns true if this node has been deleted by GC during sweep phase. */\n\tisNodeDeleted(nodePath: string): boolean;\n\tsetConnectionState(connected: boolean, clientId?: string): void;\n\tdispose(): void;\n}\n\n/** Parameters necessary for creating a GarbageCollector. */\nexport interface IGarbageCollectorCreateParams {\n\treadonly runtime: IGarbageCollectionRuntime;\n\treadonly gcOptions: IGCRuntimeOptions;\n\treadonly baseLogger: ITelemetryLogger;\n\treadonly existing: boolean;\n\treadonly metadata: IContainerRuntimeMetadata | undefined;\n\treadonly createContainerMetadata: ICreateContainerMetadata;\n\treadonly baseSnapshot: ISnapshotTree | undefined;\n\treadonly isSummarizerClient: boolean;\n\treadonly getNodePackagePath: (nodePath: string) => Promise<readonly string[] | undefined>;\n\treadonly getLastSummaryTimestampMs: () => number | undefined;\n\treadonly readAndParseBlob: ReadAndParseBlob;\n\treadonly activeConnection: () => boolean;\n\treadonly getContainerDiagnosticId: () => string;\n}\n\nexport interface IGCRuntimeOptions {\n\t/**\n\t * Flag that if true, will enable running garbage collection (GC) for a new container.\n\t *\n\t * GC has mark phase and sweep phase. In mark phase, unreferenced objects are identified\n\t * and marked as such in the summary. This option enables the mark phase.\n\t * In sweep phase, unreferenced objects are eventually deleted from the container if they meet certain conditions.\n\t * Sweep phase can be enabled via the \"sweepAllowed\" option.\n\t *\n\t * Note: This setting is persisted in the container's summary and cannot be changed.\n\t */\n\tgcAllowed?: boolean;\n\n\t/**\n\t * @deprecated - @see gcSweepGenerationOptionName and @see GCFeatureMatrix.sweepGeneration\n\t *\n\t * Flag that if true, enables GC's sweep phase for a new container.\n\t *\n\t * This will allow GC to eventually delete unreferenced objects from the container.\n\t * This flag should only be set to true if \"gcAllowed\" is true.\n\t *\n\t * Note: This setting is persisted in the container's summary and cannot be changed.\n\t */\n\tsweepAllowed?: boolean;\n\n\t/**\n\t * Flag that if true, will disable garbage collection for the session.\n\t * Can be used to disable running GC on containers where it is allowed via the gcAllowed option.\n\t */\n\tdisableGC?: boolean;\n\n\t/**\n\t * Flag that will bypass optimizations and generate GC data for all nodes irrespective of whether a node\n\t * changed or not.\n\t */\n\trunFullGC?: boolean;\n\n\t/**\n\t * Maximum session duration for a new container. If not present, a default value will be used.\n\t *\n\t * Note: This setting is persisted in the container's summary and cannot be changed.\n\t */\n\tsessionExpiryTimeoutMs?: number;\n\n\t/**\n\t * Allows additional GC options to be passed.\n\t */\n\t[key: string]: any;\n}\n\n/**\n * The configurations for Garbage Collector that determines what runs and how.\n */\nexport interface IGarbageCollectorConfigs {\n\t/**\n\t * Tracks if GC is enabled for this document. This is specified during document creation and doesn't change\n\t * throughout its lifetime.\n\t */\n\treadonly gcEnabled: boolean;\n\t/**\n\t * Tracks if sweep phase is enabled for this document. This is specified during document creation and doesn't change\n\t * throughout its lifetime.\n\t */\n\treadonly sweepEnabled: boolean;\n\t/**\n\t * Tracks if GC should run or not. Even if GC is enabled for a document (see gcEnabled), it can be explicitly\n\t * disabled via runtime options or feature flags.\n\t */\n\treadonly shouldRunGC: boolean;\n\t/**\n\t * Tracks if sweep phase should run or not. Even if the sweep phase is enabled for a document (see sweepEnabled), it\n\t * can be explicitly disabled via feature flags. It also won't run if session expiry is not enabled.\n\t */\n\treadonly shouldRunSweep: boolean;\n\t/**\n\t * If true, bypass optimizations and generate GC data for all nodes irrespective of whether a node changed or not.\n\t */\n\treadonly runFullGC: boolean | undefined;\n\t/** The time in ms to expire a session for a client for gc. */\n\treadonly sessionExpiryTimeoutMs: number | undefined;\n\t/** The time after which an unreferenced node is ready to be swept. */\n\treadonly sweepTimeoutMs: number | undefined;\n\t/** The time after which an unreferenced node is inactive. */\n\treadonly inactiveTimeoutMs: number;\n\t/** Tracks whether GC should run in test mode. In this mode, unreferenced objects are deleted immediately. */\n\treadonly testMode: boolean;\n\t/**\n\t * Tracks whether GC should run in tombstone mode. In this mode, sweep ready objects are marked as tombstones.\n\t * In interactive (non-summarizer) clients, tombstone objects behave as if they are deleted, i.e., access to them\n\t * is not allowed. However, these objects can be accessed after referencing them first. It is used as a staging\n\t * step for sweep where accidental sweep ready objects can be recovered.\n\t */\n\treadonly tombstoneMode: boolean;\n\t/** @see GCFeatureMatrix. */\n\treadonly persistedGcFeatureMatrix: GCFeatureMatrix | undefined;\n\t/** The version of GC in the base snapshot. */\n\treadonly gcVersionInBaseSnapshot: GCVersion | undefined;\n\t/** The current version of GC data in the running code */\n\treadonly gcVersionInEffect: GCVersion;\n}\n\n/** The state of node that is unreferenced. */\nexport const UnreferencedState = {\n\t/** The node is active, i.e., it can become referenced again. */\n\tActive: \"Active\",\n\t/** The node is inactive, i.e., it should not become referenced. */\n\tInactive: \"Inactive\",\n\t/** The node is ready to be deleted by the sweep phase. */\n\tSweepReady: \"SweepReady\",\n} as const;\nexport type UnreferencedState = typeof UnreferencedState[keyof typeof UnreferencedState];\n"]}
@@ -8,7 +8,7 @@ import { IGarbageCollectionSnapshotData, IGarbageCollectionState } from "@fluidf
8
8
  import { ReadAndParseBlob } from "@fluidframework/runtime-utils";
9
9
  import { MonitoringContext } from "@fluidframework/telemetry-utils";
10
10
  import { IContainerRuntimeMetadata } from "../summary";
11
- import { GCVersion, IGCMetadata } from "./gcDefinitions";
11
+ import { GCFeatureMatrix, GCVersion, IGCMetadata } from "./gcDefinitions";
12
12
  export declare function getGCVersion(metadata?: IGCMetadata): GCVersion;
13
13
  /**
14
14
  * Consolidates info / logic for logging when we encounter unexpected usage of GC'd objects. For example, when a
@@ -19,16 +19,36 @@ export declare function sendGCUnexpectedUsageEvent(mc: MonitoringContext, event:
19
19
  gcTombstoneEnforcementAllowed: boolean | undefined;
20
20
  }, packagePath: readonly string[] | undefined, error?: unknown): void;
21
21
  /**
22
+ * Indicates whether Tombstone Enforcement is allowed for this document based on the current/persisted
23
+ * TombstoneGeneration values
24
+ *
22
25
  * In order to protect old documents that were created at a time when known bugs exist that violate GC's invariants
23
- * such that enforcing GC (Fail on Tombstone load/usage, GC Sweep) would cause legitimate data loss,
26
+ * such that enforcing GC Tombstone (Failing on Tombstone load/usage) would cause legitimate data loss,
24
27
  * the container author may increment the generation value for Tombstone such that containers created
25
28
  * with a different value will not be subjected to GC enforcement.
29
+ *
26
30
  * If no generation is provided at runtime, this defaults to return true to maintain expected default behavior
27
- * @param persistedGeneration - The persisted feature support value
28
- * @param currentGeneration - The current app-provided feature support value
29
- * @returns true if GC Enforcement (Fail on Tombstone load/usage) should be allowed
31
+ *
32
+ * @param persistedGeneration - The persisted tombstoneGeneration value
33
+ * @param currentGeneration - The current app-provided tombstoneGeneration value
34
+ * @returns true if GC Tombstone enforcement (Fail on Tombstone load/usage) should be allowed for this document
30
35
  */
31
36
  export declare function shouldAllowGcTombstoneEnforcement(persistedGeneration: number | undefined, currentGeneration: number | undefined): boolean;
37
+ /**
38
+ * Indicates whether Sweep is allowed for this document based on the GC Feature Matrix and current SweepGeneration
39
+ *
40
+ * In order to protect old documents that were created at a time when known bugs exist that violate GC's invariants
41
+ * such that enforcing GC Sweep would cause legitimate data loss, the container author may increment the generation value for Sweep
42
+ * such that containers created with a different value will not be subjected to GC Sweep.
43
+ *
44
+ * If no generation is provided, Sweep will be disabled.
45
+ * Passing 0 is a special case: Sweep will be enabled for any document with gcSweepGeneration OR gcTombstoneGeneration as 0.
46
+ *
47
+ * @param persistedGenerations - The persisted sweep/tombstone generations from the GC Feature Matrix
48
+ * @param currentGeneration - The current app-provided sweepGeneration value
49
+ * @returns true if GC Sweep should be allowed for this document
50
+ */
51
+ export declare function shouldAllowGcSweep(persistedGenerations: Pick<GCFeatureMatrix, "sweepGeneration" | "tombstoneGeneration">, currentGeneration: number | undefined): boolean;
32
52
  /**
33
53
  * Sorts the given GC state as per the id of the GC nodes. It also sorts the outbound routes array of each node.
34
54
  */
@@ -1 +1 @@
1
- {"version":3,"file":"gcHelpers.d.ts","sourceRoot":"","sources":["../../src/gc/gcHelpers.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,EAAE,sBAAsB,EAAE,MAAM,oCAAoC,CAAC;AAE5E,OAAO,EAAE,aAAa,EAAE,MAAM,sCAAsC,CAAC;AACrE,OAAO,EAGN,8BAA8B,EAC9B,uBAAuB,EAEvB,MAAM,qCAAqC,CAAC;AAC7C,OAAO,EAAkC,gBAAgB,EAAE,MAAM,+BAA+B,CAAC;AACjG,OAAO,EAAE,iBAAiB,EAAE,MAAM,iCAAiC,CAAC;AAEpE,OAAO,EAEN,yBAAyB,EAEzB,MAAM,YAAY,CAAC;AACpB,OAAO,EAEN,SAAS,EACT,WAAW,EAIX,MAAM,iBAAiB,CAAC;AAEzB,wBAAgB,YAAY,CAAC,QAAQ,CAAC,EAAE,WAAW,GAAG,SAAS,CAM9D;AAED;;;GAGG;AACH,wBAAgB,0BAA0B,CACzC,EAAE,EAAE,iBAAiB,EACrB,KAAK,EAAE,sBAAsB,GAAG;IAC/B,QAAQ,EAAE,OAAO,GAAG,SAAS,CAAC;IAC9B,6BAA6B,EAAE,OAAO,GAAG,SAAS,CAAC;CACnD,EACD,WAAW,EAAE,SAAS,MAAM,EAAE,GAAG,SAAS,EAC1C,KAAK,CAAC,EAAE,OAAO,QAaf;AAED;;;;;;;;;GASG;AACH,wBAAgB,iCAAiC,CAChD,mBAAmB,EAAE,MAAM,GAAG,SAAS,EACvC,iBAAiB,EAAE,MAAM,GAAG,SAAS,GACnC,OAAO,CAMT;AAED;;GAEG;AACH,wBAAgB,qBAAqB,CAAC,OAAO,EAAE,uBAAuB,GAAG,uBAAuB,CAS/F;AAED;;;GAGG;AACH,wBAAsB,oCAAoC,CACzD,WAAW,EAAE,aAAa,EAC1B,QAAQ,EAAE,yBAAyB,GAAG,SAAS,EAC/C,gBAAgB,EAAE,gBAAgB,GAChC,OAAO,CAAC,8BAA8B,GAAG,SAAS,CAAC,CAqDrD"}
1
+ {"version":3,"file":"gcHelpers.d.ts","sourceRoot":"","sources":["../../src/gc/gcHelpers.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,EAAE,sBAAsB,EAAE,MAAM,oCAAoC,CAAC;AAE5E,OAAO,EAAE,aAAa,EAAE,MAAM,sCAAsC,CAAC;AACrE,OAAO,EAGN,8BAA8B,EAC9B,uBAAuB,EAEvB,MAAM,qCAAqC,CAAC;AAC7C,OAAO,EAAkC,gBAAgB,EAAE,MAAM,+BAA+B,CAAC;AACjG,OAAO,EAAE,iBAAiB,EAAE,MAAM,iCAAiC,CAAC;AAEpE,OAAO,EAEN,yBAAyB,EAEzB,MAAM,YAAY,CAAC;AACpB,OAAO,EAEN,eAAe,EACf,SAAS,EACT,WAAW,EAIX,MAAM,iBAAiB,CAAC;AAEzB,wBAAgB,YAAY,CAAC,QAAQ,CAAC,EAAE,WAAW,GAAG,SAAS,CAM9D;AAED;;;GAGG;AACH,wBAAgB,0BAA0B,CACzC,EAAE,EAAE,iBAAiB,EACrB,KAAK,EAAE,sBAAsB,GAAG;IAC/B,QAAQ,EAAE,OAAO,GAAG,SAAS,CAAC;IAC9B,6BAA6B,EAAE,OAAO,GAAG,SAAS,CAAC;CACnD,EACD,WAAW,EAAE,SAAS,MAAM,EAAE,GAAG,SAAS,EAC1C,KAAK,CAAC,EAAE,OAAO,QAaf;AAED;;;;;;;;;;;;;;GAcG;AACH,wBAAgB,iCAAiC,CAChD,mBAAmB,EAAE,MAAM,GAAG,SAAS,EACvC,iBAAiB,EAAE,MAAM,GAAG,SAAS,GACnC,OAAO,CAMT;AAED;;;;;;;;;;;;;GAaG;AACH,wBAAgB,kBAAkB,CACjC,oBAAoB,EAAE,IAAI,CAAC,eAAe,EAAE,iBAAiB,GAAG,qBAAqB,CAAC,EACtF,iBAAiB,EAAE,MAAM,GAAG,SAAS,GACnC,OAAO,CAgBT;AAED;;GAEG;AACH,wBAAgB,qBAAqB,CAAC,OAAO,EAAE,uBAAuB,GAAG,uBAAuB,CAS/F;AAED;;;GAGG;AACH,wBAAsB,oCAAoC,CACzD,WAAW,EAAE,aAAa,EAC1B,QAAQ,EAAE,yBAAyB,GAAG,SAAS,EAC/C,gBAAgB,EAAE,gBAAgB,GAChC,OAAO,CAAC,8BAA8B,GAAG,SAAS,CAAC,CAqDrD"}
@@ -33,14 +33,19 @@ export function sendGCUnexpectedUsageEvent(mc, event, packagePath, error) {
33
33
  mc.logger.sendTelemetryEvent(event, error);
34
34
  }
35
35
  /**
36
+ * Indicates whether Tombstone Enforcement is allowed for this document based on the current/persisted
37
+ * TombstoneGeneration values
38
+ *
36
39
  * In order to protect old documents that were created at a time when known bugs exist that violate GC's invariants
37
- * such that enforcing GC (Fail on Tombstone load/usage, GC Sweep) would cause legitimate data loss,
40
+ * such that enforcing GC Tombstone (Failing on Tombstone load/usage) would cause legitimate data loss,
38
41
  * the container author may increment the generation value for Tombstone such that containers created
39
42
  * with a different value will not be subjected to GC enforcement.
43
+ *
40
44
  * If no generation is provided at runtime, this defaults to return true to maintain expected default behavior
41
- * @param persistedGeneration - The persisted feature support value
42
- * @param currentGeneration - The current app-provided feature support value
43
- * @returns true if GC Enforcement (Fail on Tombstone load/usage) should be allowed
45
+ *
46
+ * @param persistedGeneration - The persisted tombstoneGeneration value
47
+ * @param currentGeneration - The current app-provided tombstoneGeneration value
48
+ * @returns true if GC Tombstone enforcement (Fail on Tombstone load/usage) should be allowed for this document
44
49
  */
45
50
  export function shouldAllowGcTombstoneEnforcement(persistedGeneration, currentGeneration) {
46
51
  // If no Generation value is provided for this session, then we should default to letting Tombstone feature behave as intended.
@@ -49,6 +54,33 @@ export function shouldAllowGcTombstoneEnforcement(persistedGeneration, currentGe
49
54
  }
50
55
  return persistedGeneration === currentGeneration;
51
56
  }
57
+ /**
58
+ * Indicates whether Sweep is allowed for this document based on the GC Feature Matrix and current SweepGeneration
59
+ *
60
+ * In order to protect old documents that were created at a time when known bugs exist that violate GC's invariants
61
+ * such that enforcing GC Sweep would cause legitimate data loss, the container author may increment the generation value for Sweep
62
+ * such that containers created with a different value will not be subjected to GC Sweep.
63
+ *
64
+ * If no generation is provided, Sweep will be disabled.
65
+ * Passing 0 is a special case: Sweep will be enabled for any document with gcSweepGeneration OR gcTombstoneGeneration as 0.
66
+ *
67
+ * @param persistedGenerations - The persisted sweep/tombstone generations from the GC Feature Matrix
68
+ * @param currentGeneration - The current app-provided sweepGeneration value
69
+ * @returns true if GC Sweep should be allowed for this document
70
+ */
71
+ export function shouldAllowGcSweep(persistedGenerations, currentGeneration) {
72
+ // If no Generation value is provided for this session, default to false
73
+ if (currentGeneration === undefined) {
74
+ return false;
75
+ }
76
+ // 0 is a special case: It matches both SweepGeneration and TombstoneGeneration
77
+ // This is an optimistic measure to maximize coverage of GC Sweep if no bumps to TombstoneGeneration are needed before enabling Sweep.
78
+ if (currentGeneration === 0) {
79
+ return (persistedGenerations.sweepGeneration === 0 ||
80
+ persistedGenerations.tombstoneGeneration === 0);
81
+ }
82
+ return persistedGenerations.sweepGeneration === currentGeneration;
83
+ }
52
84
  /**
53
85
  * Sorts the given GC state as per the id of the GC nodes. It also sorts the outbound routes array of each node.
54
86
  */
@@ -1 +1 @@
1
- {"version":3,"file":"gcHelpers.js","sourceRoot":"","sources":["../../src/gc/gcHelpers.ts"],"names":[],"mappings":"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","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n */\n\nimport { ITelemetryGenericEvent } from \"@fluidframework/common-definitions\";\nimport { assert } from \"@fluidframework/common-utils\";\nimport { ISnapshotTree } from \"@fluidframework/protocol-definitions\";\nimport {\n\tgcTreeKey,\n\tIGarbageCollectionNodeData,\n\tIGarbageCollectionSnapshotData,\n\tIGarbageCollectionState,\n\tIGarbageCollectionSummaryDetailsLegacy,\n} from \"@fluidframework/runtime-definitions\";\nimport { packagePathToTelemetryProperty, ReadAndParseBlob } from \"@fluidframework/runtime-utils\";\nimport { MonitoringContext } from \"@fluidframework/telemetry-utils\";\nimport { getSummaryForDatastores } from \"../dataStores\";\nimport {\n\tdataStoreAttributesBlobName,\n\tIContainerRuntimeMetadata,\n\tReadFluidDataStoreAttributes,\n} from \"../summary\";\nimport {\n\tdisableTombstoneKey,\n\tGCVersion,\n\tIGCMetadata,\n\trunSweepKey,\n\tthrowOnTombstoneLoadKey,\n\tthrowOnTombstoneUsageKey,\n} from \"./gcDefinitions\";\n\nexport function getGCVersion(metadata?: IGCMetadata): GCVersion {\n\tif (!metadata) {\n\t\t// Force to 0/disallowed in prior versions\n\t\treturn 0;\n\t}\n\treturn metadata.gcFeature ?? 0;\n}\n\n/**\n * Consolidates info / logic for logging when we encounter unexpected usage of GC'd objects. For example, when a\n * tombstoned or deleted object is loaded.\n */\nexport function sendGCUnexpectedUsageEvent(\n\tmc: MonitoringContext,\n\tevent: ITelemetryGenericEvent & {\n\t\tcategory: \"error\" | \"generic\";\n\t\tgcTombstoneEnforcementAllowed: boolean | undefined;\n\t},\n\tpackagePath: readonly string[] | undefined,\n\terror?: unknown,\n) {\n\tevent.pkg = packagePathToTelemetryProperty(packagePath);\n\tevent.tombstoneFlags = JSON.stringify({\n\t\tDisableTombstone: mc.config.getBoolean(disableTombstoneKey),\n\t\tThrowOnTombstoneUsage: mc.config.getBoolean(throwOnTombstoneUsageKey),\n\t\tThrowOnTombstoneLoad: mc.config.getBoolean(throwOnTombstoneLoadKey),\n\t});\n\tevent.sweepFlags = JSON.stringify({\n\t\tEnableSweepFlag: mc.config.getBoolean(runSweepKey),\n\t});\n\n\tmc.logger.sendTelemetryEvent(event, error);\n}\n\n/**\n * In order to protect old documents that were created at a time when known bugs exist that violate GC's invariants\n * such that enforcing GC (Fail on Tombstone load/usage, GC Sweep) would cause legitimate data loss,\n * the container author may increment the generation value for Tombstone such that containers created\n * with a different value will not be subjected to GC enforcement.\n * If no generation is provided at runtime, this defaults to return true to maintain expected default behavior\n * @param persistedGeneration - The persisted feature support value\n * @param currentGeneration - The current app-provided feature support value\n * @returns true if GC Enforcement (Fail on Tombstone load/usage) should be allowed\n */\nexport function shouldAllowGcTombstoneEnforcement(\n\tpersistedGeneration: number | undefined,\n\tcurrentGeneration: number | undefined,\n): boolean {\n\t// If no Generation value is provided for this session, then we should default to letting Tombstone feature behave as intended.\n\tif (currentGeneration === undefined) {\n\t\treturn true;\n\t}\n\treturn persistedGeneration === currentGeneration;\n}\n\n/**\n * Sorts the given GC state as per the id of the GC nodes. It also sorts the outbound routes array of each node.\n */\nexport function generateSortedGCState(gcState: IGarbageCollectionState): IGarbageCollectionState {\n\tconst sortableArray: [string, IGarbageCollectionNodeData][] = Object.entries(gcState.gcNodes);\n\tsortableArray.sort(([a], [b]) => a.localeCompare(b));\n\tconst sortedGCState: IGarbageCollectionState = { gcNodes: {} };\n\tfor (const [nodeId, nodeData] of sortableArray) {\n\t\tnodeData.outboundRoutes.sort();\n\t\tsortedGCState.gcNodes[nodeId] = nodeData;\n\t}\n\treturn sortedGCState;\n}\n\n/**\n * This is for back-compat only - Before GC data was written at the root of the summary tree, individual GC blobs were\n * written at data store's snapshot tree. This function consolidates them into the new IGarbageCollectionState format.\n */\nexport async function getSnapshotDataFromOldSnapshotFormat(\n\toldSnapshot: ISnapshotTree,\n\tmetadata: IContainerRuntimeMetadata | undefined,\n\treadAndParseBlob: ReadAndParseBlob,\n): Promise<IGarbageCollectionSnapshotData | undefined> {\n\t// Add a node for the root node that is not present in older snapshot format.\n\tconst gcState: IGarbageCollectionState = {\n\t\tgcNodes: { \"/\": { outboundRoutes: [] } },\n\t};\n\tconst dataStoreSnapshotTree = getSummaryForDatastores(oldSnapshot, metadata);\n\tassert(\n\t\tdataStoreSnapshotTree !== undefined,\n\t\t0x2a8 /* \"Expected data store snapshot tree in base snapshot\" */,\n\t);\n\tfor (const [dsId, dsSnapshotTree] of Object.entries(dataStoreSnapshotTree.trees)) {\n\t\tconst blobId = dsSnapshotTree.blobs[gcTreeKey];\n\t\tif (blobId === undefined) {\n\t\t\tcontinue;\n\t\t}\n\n\t\tconst gcSummaryDetails = await readAndParseBlob<IGarbageCollectionSummaryDetailsLegacy>(\n\t\t\tblobId,\n\t\t);\n\t\t// If there are no nodes for this data store, skip it.\n\t\tif (gcSummaryDetails.gcData?.gcNodes === undefined) {\n\t\t\tcontinue;\n\t\t}\n\n\t\tconst dsRootId = `/${dsId}`;\n\t\t// Since we used to write GC data at data store level, we won't have an entry for the root (\"/\").\n\t\t// Construct that entry by adding root data store ids to its outbound routes.\n\t\tconst initialSnapshotDetails = await readAndParseBlob<ReadFluidDataStoreAttributes>(\n\t\t\tdsSnapshotTree.blobs[dataStoreAttributesBlobName],\n\t\t);\n\t\tif (initialSnapshotDetails.isRootDataStore) {\n\t\t\tgcState.gcNodes[\"/\"].outboundRoutes.push(dsRootId);\n\t\t}\n\n\t\tfor (const [id, outboundRoutes] of Object.entries(gcSummaryDetails.gcData.gcNodes)) {\n\t\t\t// Prefix the data store id to the GC node ids to make them relative to the root from being\n\t\t\t// relative to the data store. Similar to how its done in DataStore::getGCData.\n\t\t\tconst rootId = id === \"/\" ? dsRootId : `${dsRootId}${id}`;\n\t\t\tgcState.gcNodes[rootId] = {\n\t\t\t\toutboundRoutes: Array.from(outboundRoutes),\n\t\t\t};\n\t\t}\n\t\tassert(\n\t\t\tgcState.gcNodes[dsRootId] !== undefined,\n\t\t\t0x2a9 /* GC nodes for data store not in GC blob */,\n\t\t);\n\t\tgcState.gcNodes[dsRootId].unreferencedTimestampMs = gcSummaryDetails.unrefTimestamp;\n\t}\n\t// If there is only one node (root node just added above), either GC is disabled or we are loading from\n\t// the first summary generated by detached container. In both cases, GC was not run - return undefined.\n\treturn Object.keys(gcState.gcNodes).length === 1\n\t\t? undefined\n\t\t: { gcState, tombstones: undefined, deletedNodes: undefined };\n}\n"]}
1
+ {"version":3,"file":"gcHelpers.js","sourceRoot":"","sources":["../../src/gc/gcHelpers.ts"],"names":[],"mappings":"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","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n */\n\nimport { ITelemetryGenericEvent } from \"@fluidframework/common-definitions\";\nimport { assert } from \"@fluidframework/common-utils\";\nimport { ISnapshotTree } from \"@fluidframework/protocol-definitions\";\nimport {\n\tgcTreeKey,\n\tIGarbageCollectionNodeData,\n\tIGarbageCollectionSnapshotData,\n\tIGarbageCollectionState,\n\tIGarbageCollectionSummaryDetailsLegacy,\n} from \"@fluidframework/runtime-definitions\";\nimport { packagePathToTelemetryProperty, ReadAndParseBlob } from \"@fluidframework/runtime-utils\";\nimport { MonitoringContext } from \"@fluidframework/telemetry-utils\";\nimport { getSummaryForDatastores } from \"../dataStores\";\nimport {\n\tdataStoreAttributesBlobName,\n\tIContainerRuntimeMetadata,\n\tReadFluidDataStoreAttributes,\n} from \"../summary\";\nimport {\n\tdisableTombstoneKey,\n\tGCFeatureMatrix,\n\tGCVersion,\n\tIGCMetadata,\n\trunSweepKey,\n\tthrowOnTombstoneLoadKey,\n\tthrowOnTombstoneUsageKey,\n} from \"./gcDefinitions\";\n\nexport function getGCVersion(metadata?: IGCMetadata): GCVersion {\n\tif (!metadata) {\n\t\t// Force to 0/disallowed in prior versions\n\t\treturn 0;\n\t}\n\treturn metadata.gcFeature ?? 0;\n}\n\n/**\n * Consolidates info / logic for logging when we encounter unexpected usage of GC'd objects. For example, when a\n * tombstoned or deleted object is loaded.\n */\nexport function sendGCUnexpectedUsageEvent(\n\tmc: MonitoringContext,\n\tevent: ITelemetryGenericEvent & {\n\t\tcategory: \"error\" | \"generic\";\n\t\tgcTombstoneEnforcementAllowed: boolean | undefined;\n\t},\n\tpackagePath: readonly string[] | undefined,\n\terror?: unknown,\n) {\n\tevent.pkg = packagePathToTelemetryProperty(packagePath);\n\tevent.tombstoneFlags = JSON.stringify({\n\t\tDisableTombstone: mc.config.getBoolean(disableTombstoneKey),\n\t\tThrowOnTombstoneUsage: mc.config.getBoolean(throwOnTombstoneUsageKey),\n\t\tThrowOnTombstoneLoad: mc.config.getBoolean(throwOnTombstoneLoadKey),\n\t});\n\tevent.sweepFlags = JSON.stringify({\n\t\tEnableSweepFlag: mc.config.getBoolean(runSweepKey),\n\t});\n\n\tmc.logger.sendTelemetryEvent(event, error);\n}\n\n/**\n * Indicates whether Tombstone Enforcement is allowed for this document based on the current/persisted\n * TombstoneGeneration values\n *\n * In order to protect old documents that were created at a time when known bugs exist that violate GC's invariants\n * such that enforcing GC Tombstone (Failing on Tombstone load/usage) would cause legitimate data loss,\n * the container author may increment the generation value for Tombstone such that containers created\n * with a different value will not be subjected to GC enforcement.\n *\n * If no generation is provided at runtime, this defaults to return true to maintain expected default behavior\n *\n * @param persistedGeneration - The persisted tombstoneGeneration value\n * @param currentGeneration - The current app-provided tombstoneGeneration value\n * @returns true if GC Tombstone enforcement (Fail on Tombstone load/usage) should be allowed for this document\n */\nexport function shouldAllowGcTombstoneEnforcement(\n\tpersistedGeneration: number | undefined,\n\tcurrentGeneration: number | undefined,\n): boolean {\n\t// If no Generation value is provided for this session, then we should default to letting Tombstone feature behave as intended.\n\tif (currentGeneration === undefined) {\n\t\treturn true;\n\t}\n\treturn persistedGeneration === currentGeneration;\n}\n\n/**\n * Indicates whether Sweep is allowed for this document based on the GC Feature Matrix and current SweepGeneration\n *\n * In order to protect old documents that were created at a time when known bugs exist that violate GC's invariants\n * such that enforcing GC Sweep would cause legitimate data loss, the container author may increment the generation value for Sweep\n * such that containers created with a different value will not be subjected to GC Sweep.\n *\n * If no generation is provided, Sweep will be disabled.\n * Passing 0 is a special case: Sweep will be enabled for any document with gcSweepGeneration OR gcTombstoneGeneration as 0.\n *\n * @param persistedGenerations - The persisted sweep/tombstone generations from the GC Feature Matrix\n * @param currentGeneration - The current app-provided sweepGeneration value\n * @returns true if GC Sweep should be allowed for this document\n */\nexport function shouldAllowGcSweep(\n\tpersistedGenerations: Pick<GCFeatureMatrix, \"sweepGeneration\" | \"tombstoneGeneration\">,\n\tcurrentGeneration: number | undefined,\n): boolean {\n\t// If no Generation value is provided for this session, default to false\n\tif (currentGeneration === undefined) {\n\t\treturn false;\n\t}\n\n\t// 0 is a special case: It matches both SweepGeneration and TombstoneGeneration\n\t// This is an optimistic measure to maximize coverage of GC Sweep if no bumps to TombstoneGeneration are needed before enabling Sweep.\n\tif (currentGeneration === 0) {\n\t\treturn (\n\t\t\tpersistedGenerations.sweepGeneration === 0 ||\n\t\t\tpersistedGenerations.tombstoneGeneration === 0\n\t\t);\n\t}\n\n\treturn persistedGenerations.sweepGeneration === currentGeneration;\n}\n\n/**\n * Sorts the given GC state as per the id of the GC nodes. It also sorts the outbound routes array of each node.\n */\nexport function generateSortedGCState(gcState: IGarbageCollectionState): IGarbageCollectionState {\n\tconst sortableArray: [string, IGarbageCollectionNodeData][] = Object.entries(gcState.gcNodes);\n\tsortableArray.sort(([a], [b]) => a.localeCompare(b));\n\tconst sortedGCState: IGarbageCollectionState = { gcNodes: {} };\n\tfor (const [nodeId, nodeData] of sortableArray) {\n\t\tnodeData.outboundRoutes.sort();\n\t\tsortedGCState.gcNodes[nodeId] = nodeData;\n\t}\n\treturn sortedGCState;\n}\n\n/**\n * This is for back-compat only - Before GC data was written at the root of the summary tree, individual GC blobs were\n * written at data store's snapshot tree. This function consolidates them into the new IGarbageCollectionState format.\n */\nexport async function getSnapshotDataFromOldSnapshotFormat(\n\toldSnapshot: ISnapshotTree,\n\tmetadata: IContainerRuntimeMetadata | undefined,\n\treadAndParseBlob: ReadAndParseBlob,\n): Promise<IGarbageCollectionSnapshotData | undefined> {\n\t// Add a node for the root node that is not present in older snapshot format.\n\tconst gcState: IGarbageCollectionState = {\n\t\tgcNodes: { \"/\": { outboundRoutes: [] } },\n\t};\n\tconst dataStoreSnapshotTree = getSummaryForDatastores(oldSnapshot, metadata);\n\tassert(\n\t\tdataStoreSnapshotTree !== undefined,\n\t\t0x2a8 /* \"Expected data store snapshot tree in base snapshot\" */,\n\t);\n\tfor (const [dsId, dsSnapshotTree] of Object.entries(dataStoreSnapshotTree.trees)) {\n\t\tconst blobId = dsSnapshotTree.blobs[gcTreeKey];\n\t\tif (blobId === undefined) {\n\t\t\tcontinue;\n\t\t}\n\n\t\tconst gcSummaryDetails = await readAndParseBlob<IGarbageCollectionSummaryDetailsLegacy>(\n\t\t\tblobId,\n\t\t);\n\t\t// If there are no nodes for this data store, skip it.\n\t\tif (gcSummaryDetails.gcData?.gcNodes === undefined) {\n\t\t\tcontinue;\n\t\t}\n\n\t\tconst dsRootId = `/${dsId}`;\n\t\t// Since we used to write GC data at data store level, we won't have an entry for the root (\"/\").\n\t\t// Construct that entry by adding root data store ids to its outbound routes.\n\t\tconst initialSnapshotDetails = await readAndParseBlob<ReadFluidDataStoreAttributes>(\n\t\t\tdsSnapshotTree.blobs[dataStoreAttributesBlobName],\n\t\t);\n\t\tif (initialSnapshotDetails.isRootDataStore) {\n\t\t\tgcState.gcNodes[\"/\"].outboundRoutes.push(dsRootId);\n\t\t}\n\n\t\tfor (const [id, outboundRoutes] of Object.entries(gcSummaryDetails.gcData.gcNodes)) {\n\t\t\t// Prefix the data store id to the GC node ids to make them relative to the root from being\n\t\t\t// relative to the data store. Similar to how its done in DataStore::getGCData.\n\t\t\tconst rootId = id === \"/\" ? dsRootId : `${dsRootId}${id}`;\n\t\t\tgcState.gcNodes[rootId] = {\n\t\t\t\toutboundRoutes: Array.from(outboundRoutes),\n\t\t\t};\n\t\t}\n\t\tassert(\n\t\t\tgcState.gcNodes[dsRootId] !== undefined,\n\t\t\t0x2a9 /* GC nodes for data store not in GC blob */,\n\t\t);\n\t\tgcState.gcNodes[dsRootId].unreferencedTimestampMs = gcSummaryDetails.unrefTimestamp;\n\t}\n\t// If there is only one node (root node just added above), either GC is disabled or we are loading from\n\t// the first summary generated by detached container. In both cases, GC was not run - return undefined.\n\treturn Object.keys(gcState.gcNodes).length === 1\n\t\t? undefined\n\t\t: { gcState, tombstones: undefined, deletedNodes: undefined };\n}\n"]}
@@ -4,8 +4,8 @@
4
4
  */
5
5
  import { IGarbageCollectionSnapshotData, IGarbageCollectionState, ISummarizeResult } from "@fluidframework/runtime-definitions";
6
6
  import { ReadAndParseBlob, RefreshSummaryResult } from "@fluidframework/runtime-utils";
7
- import { MonitoringContext } from "@fluidframework/telemetry-utils";
8
7
  import { GCVersion } from "./gcDefinitions";
8
+ import { IGarbageCollectorConfigs } from ".";
9
9
  /**
10
10
  * Encapsulates the garbage collection state that is tracked across summaries.
11
11
  * It maintains the GC state as per the latest summary in by the server. It updates state when a summary tracked by this
@@ -13,15 +13,13 @@ import { GCVersion } from "./gcDefinitions";
13
13
  * On summarize, it decides whether to write new state or re-use previous summary's state.
14
14
  */
15
15
  export declare class GCSummaryStateTracker {
16
- private readonly shouldRunGC;
17
- private readonly tombstoneMode;
18
- private readonly mc;
16
+ private readonly configs;
19
17
  readonly currentGCVersion: GCVersion;
20
18
  private latestSummaryGCVersion;
21
19
  private latestSummaryData;
22
20
  private pendingSummaryData;
23
21
  private wasGCRunInLatestSummary;
24
- constructor(shouldRunGC: boolean, tombstoneMode: boolean, mc: MonitoringContext, wasGCRunInBaseSnapshot: boolean, gcVersionInBaseSnapshot: GCVersion | undefined);
22
+ constructor(configs: Pick<IGarbageCollectorConfigs, "shouldRunGC" | "tombstoneMode" | "gcVersionInBaseSnapshot" | "gcVersionInEffect">, wasGCRunInBaseSnapshot: boolean);
25
23
  /**
26
24
  * Tells whether the GC state needs to be reset. This can happen under 3 conditions:
27
25
  *
@@ -36,7 +34,7 @@ export declare class GCSummaryStateTracker {
36
34
  * Note that the state will be reset only once for the first summary generated after this returns true. After that,
37
35
  * this will return false.
38
36
  */
39
- doesGCStateNeedReset(): boolean;
37
+ get doesGCStateNeedReset(): boolean;
40
38
  /**
41
39
  * Tells whether the GC state needs to be reset in the next summary. We need to do this if:
42
40
  *
@@ -52,7 +50,7 @@ export declare class GCSummaryStateTracker {
52
50
  *
53
51
  * 4.2. This client's latest summary was updated from a snapshot that has a different GC version.
54
52
  */
55
- doesSummaryStateNeedReset(): boolean;
53
+ get doesSummaryStateNeedReset(): boolean;
56
54
  /**
57
55
  * Summarizes three component of the GC data - GC state, tombstones and deleted nodes.
58
56
  * It does incremental summary, i.e., it writes summary tree / summary blob only for the component that changed.
@@ -1 +1 @@
1
- {"version":3,"file":"gcSummaryStateTracker.d.ts","sourceRoot":"","sources":["../../src/gc/gcSummaryStateTracker.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAIH,OAAO,EAKN,8BAA8B,EAC9B,uBAAuB,EACvB,gBAAgB,EAEhB,MAAM,qCAAqC,CAAC;AAC7C,OAAO,EAEN,gBAAgB,EAChB,oBAAoB,EAEpB,MAAM,+BAA+B,CAAC;AACvC,OAAO,EAAE,iBAAiB,EAAE,MAAM,iCAAiC,CAAC;AAEpE,OAAO,EAEN,SAAS,EAGT,MAAM,iBAAiB,CAAC;AAYzB;;;;;GAKG;AACH,qBAAa,qBAAqB;IAgBhC,OAAO,CAAC,QAAQ,CAAC,WAAW;IAE5B,OAAO,CAAC,QAAQ,CAAC,aAAa;IAC9B,OAAO,CAAC,QAAQ,CAAC,EAAE;IAjBpB,SAAgB,gBAAgB,EAAE,SAAS,CAAC;IAE5C,OAAO,CAAC,sBAAsB,CAAY;IAG1C,OAAO,CAAC,iBAAiB,CAAqC;IAE9D,OAAO,CAAC,kBAAkB,CAAqC;IAG/D,OAAO,CAAC,uBAAuB,CAAU;gBAIvB,WAAW,EAAE,OAAO,EAEpB,aAAa,EAAE,OAAO,EACtB,EAAE,EAAE,iBAAiB,EAEtC,sBAAsB,EAAE,OAAO,EAE/B,uBAAuB,EAAE,SAAS,GAAG,SAAS;IAa/C;;;;;;;;;;;;;OAaG;IACI,oBAAoB,IAAI,OAAO;IAItC;;;;;;;;;;;;;;OAcG;IACI,yBAAyB,IAAI,OAAO;IAO3C;;;;;OAKG;IACI,SAAS,CACf,QAAQ,EAAE,OAAO,EACjB,UAAU,EAAE,OAAO,EACnB,OAAO,EAAE,uBAAuB,EAChC,YAAY,EAAE,GAAG,CAAC,MAAM,CAAC,EACzB,UAAU,EAAE,MAAM,EAAE,GAClB,gBAAgB,GAAG,SAAS;IAgE/B;;;;;;;;;OASG;IACH,OAAO,CAAC,kBAAkB;IAsD1B;;;OAGG;IACU,oBAAoB,CAChC,cAAc,EAAE,MAAM,GAAG,SAAS,EAClC,MAAM,EAAE,oBAAoB,EAC5B,gBAAgB,EAAE,gBAAgB,GAChC,OAAO,CAAC,8BAA8B,GAAG,SAAS,CAAC;IAyCtD;;;OAGG;IACI,2BAA2B,CAAC,cAAc,EAAE,8BAA8B,GAAG,SAAS;CAc7F"}
1
+ {"version":3,"file":"gcSummaryStateTracker.d.ts","sourceRoot":"","sources":["../../src/gc/gcSummaryStateTracker.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAIH,OAAO,EAKN,8BAA8B,EAC9B,uBAAuB,EACvB,gBAAgB,EAEhB,MAAM,qCAAqC,CAAC;AAC7C,OAAO,EAEN,gBAAgB,EAChB,oBAAoB,EAEpB,MAAM,+BAA+B,CAAC;AAEvC,OAAO,EAAE,SAAS,EAAE,MAAM,iBAAiB,CAAC;AAE5C,OAAO,EAAE,wBAAwB,EAAE,MAAM,GAAG,CAAC;AAW7C;;;;;GAKG;AACH,qBAAa,qBAAqB;IAgBhC,OAAO,CAAC,QAAQ,CAAC,OAAO;IAdzB,SAAgB,gBAAgB,EAAE,SAAS,CAAkC;IAE7E,OAAO,CAAC,sBAAsB,CAAY;IAG1C,OAAO,CAAC,iBAAiB,CAAqC;IAE9D,OAAO,CAAC,kBAAkB,CAAqC;IAG/D,OAAO,CAAC,uBAAuB,CAAU;gBAIvB,OAAO,EAAE,IAAI,CAC7B,wBAAwB,EACxB,aAAa,GAAG,eAAe,GAAG,yBAAyB,GAAG,mBAAmB,CACjF,EAED,sBAAsB,EAAE,OAAO;IAQhC;;;;;;;;;;;;;OAaG;IACH,IAAW,oBAAoB,IAAI,OAAO,CAEzC;IAED;;;;;;;;;;;;;;OAcG;IACH,IAAW,yBAAyB,IAAI,OAAO,CAK9C;IAED;;;;;OAKG;IACI,SAAS,CACf,QAAQ,EAAE,OAAO,EACjB,UAAU,EAAE,OAAO,EACnB,OAAO,EAAE,uBAAuB,EAChC,YAAY,EAAE,GAAG,CAAC,MAAM,CAAC,EACzB,UAAU,EAAE,MAAM,EAAE,GAClB,gBAAgB,GAAG,SAAS;IAgE/B;;;;;;;;;OASG;IACH,OAAO,CAAC,kBAAkB;IAsD1B;;;OAGG;IACU,oBAAoB,CAChC,cAAc,EAAE,MAAM,GAAG,SAAS,EAClC,MAAM,EAAE,oBAAoB,EAC5B,gBAAgB,EAAE,gBAAgB,GAChC,OAAO,CAAC,8BAA8B,GAAG,SAAS,CAAC;IAyCtD;;;OAGG;IACI,2BAA2B,CAAC,cAAc,EAAE,8BAA8B,GAAG,SAAS;CAc7F"}
@@ -7,7 +7,6 @@ import { SummaryType } from "@fluidframework/protocol-definitions";
7
7
  import { gcBlobPrefix, gcDeletedBlobKey, gcTombstoneBlobKey, gcTreeKey, } from "@fluidframework/runtime-definitions";
8
8
  import { mergeStats, SummaryTreeBuilder, } from "@fluidframework/runtime-utils";
9
9
  import { metadataBlobName } from "../summary";
10
- import { currentGCVersion, gcVersionUpgradeToV2Key, stableGCVersion, } from "./gcDefinitions";
11
10
  import { generateSortedGCState, getGCVersion } from "./gcHelpers";
12
11
  /**
13
12
  * Encapsulates the garbage collection state that is tracked across summaries.
@@ -18,25 +17,17 @@ import { generateSortedGCState, getGCVersion } from "./gcHelpers";
18
17
  export class GCSummaryStateTracker {
19
18
  constructor(
20
19
  // Tells whether GC should run or not.
21
- shouldRunGC,
22
- // Tells whether tombstone mode is enabled or not.
23
- tombstoneMode, mc,
20
+ configs,
24
21
  // Tells whether GC was run in the base snapshot this container loaded from.
25
- wasGCRunInBaseSnapshot,
26
- // The GC version in the base snapshot this container loaded from.
27
- gcVersionInBaseSnapshot) {
28
- this.shouldRunGC = shouldRunGC;
29
- this.tombstoneMode = tombstoneMode;
30
- this.mc = mc;
22
+ wasGCRunInBaseSnapshot) {
23
+ var _a;
24
+ this.configs = configs;
25
+ // The current version of GC running.
26
+ this.currentGCVersion = this.configs.gcVersionInEffect;
31
27
  this.wasGCRunInLatestSummary = wasGCRunInBaseSnapshot;
32
- // If version upgrade is not enabled, fall back to the stable GC version.
33
- this.currentGCVersion =
34
- this.mc.config.getBoolean(gcVersionUpgradeToV2Key) === true
35
- ? currentGCVersion
36
- : stableGCVersion;
37
28
  // For existing document, the latest summary is the one that we loaded from. So, use its GC version as the
38
29
  // latest tracked GC version. For new documents, we will be writing the first summary with the current version.
39
- this.latestSummaryGCVersion = gcVersionInBaseSnapshot !== null && gcVersionInBaseSnapshot !== void 0 ? gcVersionInBaseSnapshot : this.currentGCVersion;
30
+ this.latestSummaryGCVersion = (_a = this.configs.gcVersionInBaseSnapshot) !== null && _a !== void 0 ? _a : this.currentGCVersion;
40
31
  }
41
32
  /**
42
33
  * Tells whether the GC state needs to be reset. This can happen under 3 conditions:
@@ -52,8 +43,8 @@ export class GCSummaryStateTracker {
52
43
  * Note that the state will be reset only once for the first summary generated after this returns true. After that,
53
44
  * this will return false.
54
45
  */
55
- doesGCStateNeedReset() {
56
- return this.wasGCRunInLatestSummary !== this.shouldRunGC;
46
+ get doesGCStateNeedReset() {
47
+ return this.wasGCRunInLatestSummary !== this.configs.shouldRunGC;
57
48
  }
58
49
  /**
59
50
  * Tells whether the GC state needs to be reset in the next summary. We need to do this if:
@@ -70,9 +61,9 @@ export class GCSummaryStateTracker {
70
61
  *
71
62
  * 4.2. This client's latest summary was updated from a snapshot that has a different GC version.
72
63
  */
73
- doesSummaryStateNeedReset() {
74
- return (this.doesGCStateNeedReset() ||
75
- (this.shouldRunGC && this.latestSummaryGCVersion !== this.currentGCVersion));
64
+ get doesSummaryStateNeedReset() {
65
+ return (this.doesGCStateNeedReset ||
66
+ (this.configs.shouldRunGC && this.latestSummaryGCVersion !== this.currentGCVersion));
76
67
  }
77
68
  /**
78
69
  * Summarizes three component of the GC data - GC state, tombstones and deleted nodes.
@@ -81,7 +72,7 @@ export class GCSummaryStateTracker {
81
72
  * If none of the components changed, it returns a summary handle for the entire GC data.
82
73
  */
83
74
  summarize(fullTree, trackState, gcState, deletedNodes, tombstones) {
84
- if (!this.shouldRunGC) {
75
+ if (!this.configs.shouldRunGC) {
85
76
  return;
86
77
  }
87
78
  const serializedGCState = JSON.stringify(generateSortedGCState(gcState));
@@ -89,7 +80,7 @@ export class GCSummaryStateTracker {
89
80
  // to identify deleted nodes' usage.
90
81
  const serializedDeletedNodes = deletedNodes.size > 0 ? JSON.stringify(Array.from(deletedNodes).sort()) : undefined;
91
82
  // If running in tombstone mode, serialize and write tombstones, if any.
92
- const serializedTombstones = this.tombstoneMode
83
+ const serializedTombstones = this.configs.tombstoneMode
93
84
  ? tombstones.length > 0
94
85
  ? JSON.stringify(tombstones.sort())
95
86
  : undefined
@@ -182,9 +173,9 @@ export class GCSummaryStateTracker {
182
173
  // Note that this has to be updated if GC did not run too. Otherwise, `gcStateNeedsReset` will always return
183
174
  // true in scenarios where GC is disabled but enabled in the snapshot we loaded from.
184
175
  if (result.latestSummaryUpdated && result.wasSummaryTracked) {
185
- this.wasGCRunInLatestSummary = this.shouldRunGC;
176
+ this.wasGCRunInLatestSummary = this.configs.shouldRunGC;
186
177
  }
187
- if (!result.latestSummaryUpdated || !this.shouldRunGC) {
178
+ if (!result.latestSummaryUpdated || !this.configs.shouldRunGC) {
188
179
  return undefined;
189
180
  }
190
181
  // If the summary was tracked by this client, it was the one that generated the summary in the first place.