github.com/keybase/client/go@v0.0.0-20241007131713-f10651d043c8/kbfs/libgit/init.go (about)

     1  // Copyright 2017 Keybase Inc. All rights reserved.
     2  // Use of this source code is governed by a BSD
     3  // license that can be found in the LICENSE file.
     4  
     5  package libgit
     6  
     7  import (
     8  	"context"
     9  	"os"
    10  
    11  	"github.com/keybase/client/go/kbfs/libcontext"
    12  	"github.com/keybase/client/go/kbfs/libkbfs"
    13  	"github.com/keybase/client/go/logger"
    14  	"github.com/keybase/client/go/protocol/keybase1"
    15  )
    16  
    17  const (
    18  	// Debug tag ID for a batched set of git operations under a single
    19  	// config.
    20  	ctxGitOpID = "GITID"
    21  )
    22  
    23  type ctxGitTagKey int
    24  
    25  const (
    26  	paramKeybaseGitMDServerAddr = "KEYBASE_GIT_MDSERVER_ADDR"
    27  	paramKeybaseGitBServerAddr  = "KEYBASE_GIT_BSERVER_ADDR"
    28  )
    29  
    30  const (
    31  	ctxGitIDKey ctxGitTagKey = iota
    32  )
    33  
    34  // Params returns a set of default parameters for git-related
    35  // operations, along with a temp directory that should be cleaned
    36  // after the git work is complete.
    37  func Params(kbCtx libkbfs.Context,
    38  	storageRoot string, paramsBase *libkbfs.InitParams) (
    39  	params libkbfs.InitParams, tempDir string, err error) {
    40  	tempDir, err = os.MkdirTemp(storageRoot, libkbfs.GitStorageRootPrefix)
    41  	if err != nil {
    42  		return libkbfs.InitParams{}, "", err
    43  	}
    44  
    45  	if paramsBase != nil {
    46  		params = *paramsBase
    47  	} else {
    48  		params = libkbfs.DefaultInitParams(kbCtx)
    49  	}
    50  	params.LogToFile = true
    51  	// Set the debug default to true only if the env variable isn't
    52  	// explicitly set to a false option.
    53  	envDebug := os.Getenv("KBFSGIT_DEBUG")
    54  	if envDebug != "0" && envDebug != "false" && envDebug != "no" {
    55  		params.Debug = true
    56  	}
    57  	// This is set to false in docker tests for now, but we need it. So
    58  	// override it to true here.
    59  	params.EnableJournal = true
    60  	params.DiskCacheMode = libkbfs.DiskCacheModeRemote
    61  	params.StorageRoot = tempDir
    62  	params.Mode = libkbfs.InitSingleOpString
    63  	params.TLFJournalBackgroundWorkStatus =
    64  		libkbfs.TLFJournalSingleOpBackgroundWorkEnabled
    65  
    66  	if baddr := os.Getenv(paramKeybaseGitBServerAddr); len(baddr) > 0 {
    67  		params.BServerAddr = baddr
    68  	}
    69  	if mdaddr := os.Getenv(paramKeybaseGitMDServerAddr); len(mdaddr) > 0 {
    70  		params.MDServerAddr = mdaddr
    71  	}
    72  
    73  	return params, tempDir, nil
    74  }
    75  
    76  // Init initializes a context and a libkbfs.Config for git operations.
    77  // The config should be shutdown when it is done being used.
    78  func Init(ctx context.Context, gitKBFSParams libkbfs.InitParams,
    79  	kbCtx libkbfs.Context, keybaseServiceCn libkbfs.KeybaseServiceCn,
    80  	defaultLogPath string, vlogLevel string) (
    81  	context.Context, libkbfs.Config, error) {
    82  	log, err := libkbfs.InitLogWithPrefix(
    83  		gitKBFSParams, kbCtx, "git", defaultLogPath)
    84  	if err != nil {
    85  		return ctx, nil, err
    86  	}
    87  
    88  	// Assign a unique ID to each remote-helper instance, since
    89  	// they'll all share the same log.
    90  	ctx, err = libcontext.NewContextWithCancellationDelayer(
    91  		libkbfs.CtxWithRandomIDReplayable(
    92  			ctx, ctxGitIDKey, ctxGitOpID, log))
    93  	if err != nil {
    94  		return ctx, nil, err
    95  	}
    96  	log.CDebugf(ctx, "Initialized new git config")
    97  
    98  	config, err := libkbfs.InitWithLogPrefix(
    99  		ctx, kbCtx, gitKBFSParams, keybaseServiceCn, nil, log, "git")
   100  	if err != nil {
   101  		return ctx, nil, err
   102  	}
   103  	config.SetVLogLevel(vlogLevel)
   104  
   105  	// Make any blocks written by via this config charged to the git
   106  	// quota.
   107  	config.SetDefaultBlockType(keybase1.BlockType_GIT)
   108  
   109  	err = config.MakeDiskBlockCacheIfNotExists()
   110  	if err != nil {
   111  		log.CDebugf(ctx, "Couldn't initialize disk cache: %+v", err)
   112  	}
   113  
   114  	return ctx, config, nil
   115  }
   116  
   117  func getNewConfig(
   118  	ctx context.Context, config libkbfs.Config, kbCtx libkbfs.Context,
   119  	kbfsInitParams *libkbfs.InitParams, log logger.Logger) (
   120  	newCtx context.Context, gitConfig libkbfs.Config,
   121  	tempDir string, err error) {
   122  	// Initialize libgit.
   123  	params, tempDir, err := Params(kbCtx, config.StorageRoot(), kbfsInitParams)
   124  	if err != nil {
   125  		return nil, nil, "", err
   126  	}
   127  	defer func() {
   128  		if err != nil {
   129  			rmErr := os.RemoveAll(tempDir)
   130  			if rmErr != nil {
   131  				log.CDebugf(
   132  					ctx, "Error cleaning storage dir %s: %+v\n", tempDir, rmErr)
   133  			}
   134  		}
   135  	}()
   136  
   137  	// Let the init code know it shouldn't try to change the
   138  	// global logger settings.
   139  	params.LogToFile = false
   140  	params.LogFileConfig.Path = ""
   141  
   142  	newCtx, gitConfig, err = Init(
   143  		ctx, params, kbCtx, libkbfs.NewKeybaseServicePassthrough(config), "",
   144  		config.VLogLevel())
   145  	if err != nil {
   146  		return nil, nil, "", err
   147  	}
   148  	return newCtx, gitConfig, tempDir, nil
   149  }