|
| 1 | +/* |
| 2 | +Copyright © 2020 Alessandro Segala (@ItalyPaleAle) |
| 3 | +
|
| 4 | +This program is free software: you can redistribute it and/or modify |
| 5 | +it under the terms of the GNU General Public License as published by |
| 6 | +the Free Software Foundation, either version 3 of the License, or |
| 7 | +(at your option) any later version. |
| 8 | +
|
| 9 | +This program is distributed in the hope that it will be useful, |
| 10 | +but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 11 | +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 12 | +GNU General Public License for more details. |
| 13 | +
|
| 14 | +You should have received a copy of the GNU General Public License |
| 15 | +along with this program. If not, see <http://www.gnu.org/licenses/>. |
| 16 | +*/ |
| 17 | + |
| 18 | +package cmd |
| 19 | + |
| 20 | +import ( |
| 21 | + "context" |
| 22 | + "fmt" |
| 23 | + |
| 24 | + "github.com/ItalyPaleAle/prvt/fs" |
| 25 | + |
| 26 | + "github.com/manifoldco/promptui" |
| 27 | + "github.com/spf13/cobra" |
| 28 | +) |
| 29 | + |
| 30 | +// NewRepoLockBreakCmd is for "prvt repo lock-break" |
| 31 | +func NewRepoLockBreakCmd() *cobra.Command { |
| 32 | + c := &cobra.Command{ |
| 33 | + Use: "lock-break", |
| 34 | + Short: "Forcefully remove all locks on a repository", |
| 35 | + Long: `DATA LOSS WARNING: USE THIS COMMAND WITH CAUTION |
| 36 | +
|
| 37 | +This command forcefully removes all locks placed on a repository, allowing the usage of a repository that was otherwise locked. |
| 38 | +
|
| 39 | +Most prvt commands acquire an exclusive lock on the repository before performing operations that would change the index, to forbid other instances of prvt from accessing the same repository and so to preserve the integrity of the data. Locks are generally removed automatically once the comamnd ends or the app is closed; however, in situations such as when the app suddenly crashes, repositories may remain in a locked state. |
| 40 | +
|
| 41 | +When that happens, using the "prvt repo break-locks --store <string>" command can help by removing all locks placed on a repository. |
| 42 | +
|
| 43 | +This command should ONLY be invoked if you're sure that no other instance of prvt is accessing the data in the repository. Forcefully unlocking a repository that is in use by another instance of prvt could cause the index to be corrupted and data loss. |
| 44 | +`, |
| 45 | + DisableAutoGenTag: true, |
| 46 | + |
| 47 | + RunE: func(cmd *cobra.Command, args []string) error { |
| 48 | + // Flags |
| 49 | + flagStoreConnectionString, err := cmd.Flags().GetString("store") |
| 50 | + if err != nil { |
| 51 | + return NewExecError(ErrorApp, "Cannot get flag 'store'", err) |
| 52 | + } |
| 53 | + |
| 54 | + // Ask for confirmation |
| 55 | + prompt := promptui.Prompt{ |
| 56 | + Label: "Force break locks for repository " + flagStoreConnectionString, |
| 57 | + IsConfirm: true, |
| 58 | + Stdin: PromptuiStdin, |
| 59 | + Stdout: PromptuiStdout, |
| 60 | + } |
| 61 | + result, err := prompt.Run() |
| 62 | + if err != nil || (result != "y" && result != "Y") { |
| 63 | + // The prompt returns an error even when the user selects "n", so just abort |
| 64 | + fmt.Fprintln(cmd.OutOrStdout(), "Aborted") |
| 65 | + return nil |
| 66 | + } |
| 67 | + |
| 68 | + // Create the store object |
| 69 | + // No need for a lock for this command |
| 70 | + store, err := fs.GetWithConnectionString(flagStoreConnectionString) |
| 71 | + if err != nil || store == nil { |
| 72 | + return NewExecError(ErrorUser, "Could not initialize store", err) |
| 73 | + } |
| 74 | + |
| 75 | + // Remove all locks |
| 76 | + err = store.BreakLock(context.Background()) |
| 77 | + if err != nil { |
| 78 | + return NewExecError(ErrorApp, "Could not break locks on the repository", err) |
| 79 | + } |
| 80 | + fmt.Fprintln(cmd.OutOrStdout(), "All locks on the repository have been removed") |
| 81 | + |
| 82 | + return nil |
| 83 | + }, |
| 84 | + } |
| 85 | + |
| 86 | + // Flags |
| 87 | + addStoreFlag(c, true) |
| 88 | + |
| 89 | + return c |
| 90 | +} |
0 commit comments