2025-04-14 14:47:22 +03:00

221 lines
6.1 KiB
C++

// Copyright (c) 2014-2020 Sebastien Rombauts (sebastien.rombauts@gmail.com)
//
// Distributed under the MIT License (MIT) (See accompanying file LICENSE.txt
// or copy at http://opensource.org/licenses/MIT)
#pragma once
#include "GitSourceControlChangelist.h"
#include "GitSourceControlRevision.h"
#include "Runtime/Launch/Resources/Version.h"
/** A consolidation of state priorities. */
namespace EGitState
{
enum Type
{
Unset,
NotAtHead,
#if 0
AddedAtHead,
DeletedAtHead,
#endif
LockedOther,
NotLatest,
/** Unmerged state (modified, but conflicts) */
Unmerged,
Added,
Deleted,
Modified,
/** Not modified, but locked explicitly. */
CheckedOut,
Untracked,
Lockable,
Unmodified,
Ignored,
/** Whatever else. */
None,
};
}
/** Corresponds to diff file states. */
namespace EFileState
{
enum Type
{
Unset,
Unknown,
Added,
Copied,
Deleted,
Modified,
Renamed,
Missing,
Unmerged,
};
}
/** Where in the world is this file? */
namespace ETreeState
{
enum Type
{
Unset,
/** This file is synced to commit */
Unmodified,
/** This file is modified, but not in staging tree */
Working,
/** This file is in staging tree (git add) */
Staged,
/** This file is not tracked in the repo yet */
Untracked,
/** This file is ignored by the repo */
Ignored,
/** This file is outside the repo folder */
NotInRepo,
};
}
/** LFS locks status of this file */
namespace ELockState
{
enum Type
{
Unset,
Unknown,
Unlockable,
NotLocked,
Locked,
LockedOther,
};
}
/** What is this file doing at HEAD? */
namespace ERemoteState
{
enum Type
{
Unset,
/** Up to date */
UpToDate,
/** Local version is behind remote */
NotAtHead,
#if 0
// TODO: handle these
/** Remote file does not exist on local */
AddedAtHead,
/** Local was deleted on remote */
DeletedAtHead,
#endif
/** Not at the latest revision amongst the tracked branches */
NotLatest,
};
}
/** Combined state, for updating cache in a map. */
struct FGitState
{
EFileState::Type FileState = EFileState::Unknown;
ETreeState::Type TreeState = ETreeState::NotInRepo;
ELockState::Type LockState = ELockState::Unknown;
/** Name of user who has locked the file */
FString LockUser;
ERemoteState::Type RemoteState = ERemoteState::UpToDate;
/** The branch with the latest commit for this file */
FString HeadBranch;
};
class FGitSourceControlState : public ISourceControlState
{
public:
FGitSourceControlState(const FString &InLocalFilename)
: LocalFilename(InLocalFilename)
, TimeStamp(0)
, HeadAction(TEXT("Changed"))
, HeadCommit(TEXT("Unknown"))
{
}
/** ISourceControlState interface */
virtual int32 GetHistorySize() const override;
virtual TSharedPtr<class ISourceControlRevision, ESPMode::ThreadSafe> GetHistoryItem(int32 HistoryIndex) const override;
virtual TSharedPtr<class ISourceControlRevision, ESPMode::ThreadSafe> FindHistoryRevision(int32 RevisionNumber) const override;
virtual TSharedPtr<class ISourceControlRevision, ESPMode::ThreadSafe> FindHistoryRevision(const FString& InRevision) const override;
#if ENGINE_MAJOR_VERSION < 5 || ENGINE_MAJOR_VERSION == 5 && ENGINE_MINOR_VERSION < 3
virtual TSharedPtr<class ISourceControlRevision, ESPMode::ThreadSafe> GetBaseRevForMerge() const override;
#else
virtual FResolveInfo GetResolveInfo() const override;
#endif
#if ENGINE_MAJOR_VERSION == 5 && ENGINE_MINOR_VERSION >= 2
virtual TSharedPtr<class ISourceControlRevision, ESPMode::ThreadSafe> GetCurrentRevision() const override;
#endif
#if ENGINE_MAJOR_VERSION >= 5
virtual FSlateIcon GetIcon() const override;
#else
virtual FName GetIconName() const override;
virtual FName GetSmallIconName() const override;
#endif
virtual FText GetDisplayName() const override;
virtual FText GetDisplayTooltip() const override;
virtual const FString& GetFilename() const override;
virtual const FDateTime& GetTimeStamp() const override;
virtual bool CanCheckIn() const override;
virtual bool CanCheckout() const override;
virtual bool IsCheckedOut() const override;
virtual bool IsCheckedOutOther(FString* Who = NULL) const override;
virtual bool IsCheckedOutInOtherBranch(const FString& CurrentBranch = FString()) const override;
virtual bool IsModifiedInOtherBranch(const FString& CurrentBranch = FString()) const override;
virtual bool IsCheckedOutOrModifiedInOtherBranch(const FString& CurrentBranch = FString()) const override { return IsModifiedInOtherBranch(CurrentBranch); }
virtual TArray<FString> GetCheckedOutBranches() const override { return TArray<FString>(); }
virtual FString GetOtherUserBranchCheckedOuts() const override { return FString(); }
virtual bool GetOtherBranchHeadModification(FString& HeadBranchOut, FString& ActionOut, int32& HeadChangeListOut) const override;
virtual bool IsCurrent() const override;
virtual bool IsSourceControlled() const override;
virtual bool IsAdded() const override;
virtual bool IsDeleted() const override;
virtual bool IsIgnored() const override;
virtual bool CanEdit() const override;
virtual bool IsUnknown() const override;
virtual bool IsModified() const override;
virtual bool CanAdd() const override;
virtual bool CanDelete() const override;
virtual bool IsConflicted() const override;
virtual bool CanRevert() const override;
private:
EGitState::Type GetGitState() const;
public:
/** History of the item, if any */
TGitSourceControlHistory History;
/** Filename on disk */
FString LocalFilename;
#if ENGINE_MAJOR_VERSION == 5 && ENGINE_MINOR_VERSION >= 3
/** Pending rev info with which a file must be resolved, invalid if no resolve pending */
FResolveInfo PendingResolveInfo;
UE_DEPRECATED(5.3, "Use PendingResolveInfo.BaseRevision instead")
#endif
/** File Id with which our local revision diverged from the remote revision */
FString PendingMergeBaseFileHash;
/** Status of the file */
FGitState State;
FGitSourceControlChangelist Changelist;
/** The timestamp of the last update */
FDateTime TimeStamp;
/** The action within the head branch TODO */
FString HeadAction;
/** The last file modification time in the head branch TODO */
int64 HeadModTime;
/** The change list the last modification TODO */
FString HeadCommit;
};