github.com/nevins-b/terraform@v0.3.8-0.20170215184714-bbae22007d5a/command/state_meta.go (about) 1 package command 2 3 import ( 4 "errors" 5 "fmt" 6 "time" 7 8 backendlocal "github.com/hashicorp/terraform/backend/local" 9 "github.com/hashicorp/terraform/state" 10 "github.com/hashicorp/terraform/terraform" 11 ) 12 13 // StateMeta is the meta struct that should be embedded in state subcommands. 14 type StateMeta struct{} 15 16 // State returns the state for this meta. This is different then Meta.State 17 // in the way that backups are done. This configures backups to be timestamped 18 // rather than just the original state path plus a backup path. 19 func (c *StateMeta) State(m *Meta) (state.State, error) { 20 // Disable backups since we wrap it manually below 21 m.backupPath = "-" 22 23 // Load the backend 24 b, err := m.Backend(nil) 25 if err != nil { 26 return nil, err 27 } 28 29 // Get the state 30 s, err := b.State() 31 if err != nil { 32 return nil, err 33 } 34 35 // Get a local backend 36 localRaw, err := m.Backend(&BackendOpts{ForceLocal: true}) 37 if err != nil { 38 // This should never fail 39 panic(err) 40 } 41 localB := localRaw.(*backendlocal.Local) 42 43 // Determine the backup path. stateOutPath is set to the resulting 44 // file where state is written (cached in the case of remote state) 45 backupPath := fmt.Sprintf( 46 "%s.%d%s", 47 localB.StateOutPath, 48 time.Now().UTC().Unix(), 49 DefaultBackupExtension) 50 51 // Wrap it for backups 52 s = &state.BackupState{ 53 Real: s, 54 Path: backupPath, 55 } 56 57 return s, nil 58 } 59 60 // filterInstance filters a single instance out of filter results. 61 func (c *StateMeta) filterInstance(rs []*terraform.StateFilterResult) (*terraform.StateFilterResult, error) { 62 var result *terraform.StateFilterResult 63 for _, r := range rs { 64 if _, ok := r.Value.(*terraform.InstanceState); !ok { 65 continue 66 } 67 68 if result != nil { 69 return nil, errors.New(errStateMultiple) 70 } 71 72 result = r 73 } 74 75 return result, nil 76 } 77 78 const errStateMultiple = `Multiple instances found for the given pattern! 79 80 This command requires that the pattern match exactly one instance 81 of a resource. To view the matched instances, use "terraform state list". 82 Please modify the pattern to match only a single instance.`