github.com/opentofu/opentofu@v1.7.1/internal/states/statemgr/persistent.go (about) 1 // Copyright (c) The OpenTofu Authors 2 // SPDX-License-Identifier: MPL-2.0 3 // Copyright (c) 2023 HashiCorp, Inc. 4 // SPDX-License-Identifier: MPL-2.0 5 6 package statemgr 7 8 import ( 9 version "github.com/hashicorp/go-version" 10 11 "github.com/opentofu/opentofu/internal/states" 12 "github.com/opentofu/opentofu/internal/tofu" 13 ) 14 15 // Persistent is a union of the Refresher and Persistent interfaces, for types 16 // that deal with persistent snapshots. 17 // 18 // Persistent snapshots are ones that are retained in storage that will 19 // outlive a particular OpenTofu process, and are shared with other OpenTofu 20 // processes that have a similarly-configured state manager. 21 // 22 // A manager may also choose to retain historical persistent snapshots, but 23 // that is an implementation detail and not visible via this API. 24 type Persistent interface { 25 Refresher 26 Persister 27 OutputReader 28 } 29 30 // OutputReader is the interface for managers that fetches output values from state 31 // or another source. This is a refinement of fetching the entire state and digging 32 // the output values from it because enhanced backends can apply special permissions 33 // to differentiate reading the state and reading the outputs within the state. 34 type OutputReader interface { 35 // GetRootOutputValues fetches the root module output values from state or another source 36 GetRootOutputValues() (map[string]*states.OutputValue, error) 37 } 38 39 // Refresher is the interface for managers that can read snapshots from 40 // persistent storage. 41 // 42 // Refresher is usually implemented in conjunction with Reader, with 43 // RefreshState copying the latest persistent snapshot into the latest 44 // transient snapshot. 45 // 46 // For a type that implements both Refresher and Persister, RefreshState must 47 // return the result of the most recently completed successful call to 48 // PersistState, unless another concurrently-running process has persisted 49 // another snapshot in the mean time. 50 // 51 // The Refresher implementation must guarantee that the snapshot is read 52 // from persistent storage in a way that is safe under concurrent calls to 53 // PersistState that may be happening in other processes. 54 type Refresher interface { 55 // RefreshState retrieves a snapshot of state from persistent storage, 56 // returning an error if this is not possible. 57 // 58 // Types that implement RefreshState generally also implement a State 59 // method that returns the result of the latest successful refresh. 60 // 61 // Since only a subset of the data in a state is included when persisting, 62 // a round-trip through PersistState and then RefreshState will often 63 // return only a subset of what was written. Callers must assume that 64 // ephemeral portions of the state may be unpopulated after calling 65 // RefreshState. 66 RefreshState() error 67 } 68 69 // Persister is the interface for managers that can write snapshots to 70 // persistent storage. 71 // 72 // Persister is usually implemented in conjunction with Writer, with 73 // PersistState copying the latest transient snapshot to be the new latest 74 // persistent snapshot. 75 // 76 // A Persister implementation must detect updates made by other processes 77 // that may be running concurrently and avoid destroying those changes. This 78 // is most commonly achieved by making use of atomic write capabilities on 79 // the remote storage backend in conjunction with book-keeping with the 80 // Serial and Lineage fields in the standard state file formats. 81 // 82 // Some implementations may optionally utilize config schema to persist 83 // state. For example, when representing state in an external JSON 84 // representation. 85 type Persister interface { 86 PersistState(*tofu.Schemas) error 87 } 88 89 // PersistentMeta is an optional extension to Persistent that allows inspecting 90 // the metadata associated with the snapshot that was most recently either 91 // read by RefreshState or written by PersistState. 92 type PersistentMeta interface { 93 // StateSnapshotMeta returns metadata about the state snapshot most 94 // recently created either by a call to PersistState or read by a call 95 // to RefreshState. 96 // 97 // If no persistent snapshot is yet available in the manager then 98 // the return value is meaningless. This method is primarily available 99 // for testing and logging purposes, and is of little use otherwise. 100 StateSnapshotMeta() SnapshotMeta 101 } 102 103 // SnapshotMeta contains metadata about a persisted state snapshot. 104 // 105 // This metadata is usually (but not necessarily) included as part of the 106 // "header" of a state file, which is then written to a raw blob storage medium 107 // by a persistent state manager. 108 // 109 // Not all state managers will have useful values for all fields in this 110 // struct, so SnapshotMeta values are of little use beyond testing and logging 111 // use-cases. 112 type SnapshotMeta struct { 113 // Lineage and Serial can be used to understand the relationships between 114 // snapshots. 115 // 116 // If two snapshots both have an identical, non-empty Lineage 117 // then the one with the higher Serial is newer than the other. 118 // If the Lineage values are different or empty then the two snapshots 119 // are unrelated and cannot be compared for relative age. 120 Lineage string 121 Serial uint64 122 123 // TerraformVersion is the number of the version of OpenTofu that created 124 // the snapshot. 125 TerraformVersion *version.Version 126 }