|  | 
|  | 1 | +// Copyright (c) HashiCorp, Inc. | 
|  | 2 | +// SPDX-License-Identifier: MPL-2.0 | 
|  | 3 | + | 
|  | 4 | +package getter | 
|  | 5 | + | 
|  | 6 | +import ( | 
|  | 7 | +	"io" | 
|  | 8 | +	"os" | 
|  | 9 | +	"path/filepath" | 
|  | 10 | +) | 
|  | 11 | + | 
|  | 12 | +// mkdirTemp creates a new temporary directory that isn't yet created. This | 
|  | 13 | +// can be used with calls that expect a non-existent directory. | 
|  | 14 | +// | 
|  | 15 | +// The temporary directory is also evaluated for symlinks upon creation | 
|  | 16 | +// as some operating systems provide symlinks by default when created. | 
|  | 17 | +// | 
|  | 18 | +// The directory is created as a child of a temporary directory created | 
|  | 19 | +// within the directory dir starting with prefix. The temporary directory | 
|  | 20 | +// returned is always named "temp". The parent directory has the specified | 
|  | 21 | +// prefix. | 
|  | 22 | +// | 
|  | 23 | +// The returned io.Closer should be used to clean up the returned directory. | 
|  | 24 | +// This will properly remove the returned directory and any other temporary | 
|  | 25 | +// files created. | 
|  | 26 | +// | 
|  | 27 | +// If an error is returned, the Closer does not need to be called (and will | 
|  | 28 | +// be nil). | 
|  | 29 | +func mkdirTemp(dir, prefix string) (string, io.Closer, error) { | 
|  | 30 | +	// Create the temporary directory | 
|  | 31 | +	td, err := os.MkdirTemp(dir, prefix) | 
|  | 32 | +	if err != nil { | 
|  | 33 | +		return "", nil, err | 
|  | 34 | +	} | 
|  | 35 | + | 
|  | 36 | +	// we evaluate symlinks as some operating systems (eg: MacOS), that | 
|  | 37 | +	// actually has any temporary directory created as a symlink. | 
|  | 38 | +	// As we have only just created the temporary directory, this is a safe | 
|  | 39 | +	// evaluation to make at this time. | 
|  | 40 | +	td, err = filepath.EvalSymlinks(td) | 
|  | 41 | +	if err != nil { | 
|  | 42 | +		return "", nil, err | 
|  | 43 | +	} | 
|  | 44 | + | 
|  | 45 | +	return filepath.Join(td, "temp"), pathCloser(td), nil | 
|  | 46 | +} | 
|  | 47 | + | 
|  | 48 | +// pathCloser implements io.Closer to remove the given path on Close. | 
|  | 49 | +type pathCloser string | 
|  | 50 | + | 
|  | 51 | +// Close deletes this path. | 
|  | 52 | +func (p pathCloser) Close() error { | 
|  | 53 | +	return os.RemoveAll(string(p)) | 
|  | 54 | +} | 
0 commit comments