Área de transferência para copiar e colar arquivos na linha de comando?

23

No Bash, suponha que eu visite um diretório e, em seguida, outro diretório. Eu gostaria de copiar um arquivo do primeiro diretório para o segundo diretório, mas sem especificar os nomes dos caminhos longos deles. É possível?

Minha solução temporária é usar /tmp como um local temporário para armazenar uma cópia do arquivo. cp myfile /tmp quando estou no primeiro diretório e, em seguida, cp /tmp/myfile . quando estou no segundo diretório. Mas eu posso verificar se o arquivo irá sobrescrever qualquer coisa em /tmp .

Existe algo semelhante a uma área de transferência para copiar e colar um arquivo?

    
por Tim 10.03.2016 / 04:58

8 respostas

57

Usando o Bash, gostaria de visitar os diretórios:

$ cd /path/to/source/directory
$ cd /path/to/destination/directory

Então, eu usaria o atalho ~- , que aponta para o diretório anterior:

$ cp -v ~-/file1.txt .
$ cp -v ~-/file2.txt .
$ cp -v ~-/file3.txt .

Se alguém quiser visitar diretórios em ordem reversa, então:

$ cp -v fileA.txt ~-
$ cp -v fileB.txt ~-
$ cp -v fileC.txt ~-
    
por 10.03.2016 / 06:17
10

Se eu vi essa situação como algo único, eu poderia:

a='pwd'
cd /somewhere/else
cp "$a/myfile" .

Se houvesse diretórios em que eu me vi copiando arquivos de forma semi-regular, eu provavelmente definiria algumas variáveis mnemônicas para eles no meu .profile.

Editado para adicionar:

Depois de dormir nele, fiquei imaginando o quão próximo eu poderia chegar de outros comportamentos de GUI / OS, nos quais você seleciona alguns arquivos, "corta" ou "copia" os arquivos e os "cola" em algum outro lugar. O melhor mecanismo de seleção que eu consegui encontrar foi o seu cérebro / preferências, além do recurso globbing do shell. Eu não sou muito criativo com a nomeação, mas esta é a ideia básica (na sintaxe Bash):

function copyfiles {
  _copypastefiles=("$@")
  _copypastesrc="$PWD"
  _copypastemode=copy
}

function cutfiles {
  _copypastefiles=("$@")
  _copypastesrc="$PWD"
  _copypastemode=cut
}

function pastefiles {
  for f in "${_copypastefiles[@]}"
  do
    cp "${_copypastesrc}/$f" .
    if [[ ${_copypastemode} = "cut" ]]
    then
      rm "${_copypastesrc}/$f"
    fi
  done
}

Para usá-lo, coloque o código em ~ / .bash_profile, em seguida, cd no diretório de origem e execute copyfiles glob*here ou cutfiles glob*here . Tudo o que acontece é que o seu shell expande os globs e coloca esses nomes de arquivos em um array. Você então cd para o diretório de destino e executa pastefiles , que executa um comando cp para cada arquivo de origem. Se você tiver "recortado" anteriormente os arquivos, os pastefiles também removerão o arquivo de origem (ou tentará). Isso não faz nenhuma verificação de erros (de arquivos existentes, antes de potencialmente sufocá-los com o cp ; ou de você ter permissões para remover os arquivos durante um "recorte" ou de poder acessar novamente o diretório de origem após você sai disso).

    
por 10.03.2016 / 05:16
5

Acho que o ~- é a resposta certa, mas observe que o bash tem um editor de linhas interno que pode copiar / colar texto.

Se você estiver no modo emacs, você pode chamar o comando cd do histórico, e usar Control-u para matar a linha no bash "clipboard" chamado de kill-ring (existem outras maneiras também). Você pode então mandar essa string para um novo comando a qualquer momento com Control-y . Obviamente, no seu exemplo, isso depende de você ter usado um nome de diretório absoluto no comando cd .

Você também pode usar a interessante vinculação de chave padrão de Meta -. . Esta copia a última palavra do comando anterior para a sua linha atual. Se repetido, cada vez que voltar um comando no histórico. Então, se você fizer um cd /x , então cd /y seguido por cd Meta -. Meta -. você terá /x em sua entrada.

    
por 10.03.2016 / 08:19
5

Expandindo em a resposta de Anderson M. Gomes , o Bash permite que você consulte qualquer diretório anterior em seu pilha de diretórios, digitando ~N (ou ~+N ) onde N é a posição na pilha dir. Por exemplo:

# go some places
$ cd /path/to/source/directory
$ pushd /path/to/destination/directory
$ pushd $HOME
$ pushd /tmp

# show the current dir stack
$ dirs -v
0 /tmp
1 ~
2 /path/to/destination/directory
3 /path/to/source/directory

Agora você pode copiar um arquivo entre dois diretórios anteriores, nenhum deles o atual, com:

cp -v ~3/file1.txt ~2

Para resolver o problema do pôster original, você faria:

$ cd /path/to/source/directory
$ pushd /path/to/destination/directory

# show the current dir stack
$ dirs -v
0 /path/to/destination/directory
1 /path/to/source/directory

# copy
cp -v ~1/file[123].txt .

Com um grande conjunto de arquivos, você pode listá-los em um arquivo de manifesto e fazer a cópia a partir do diretório de origem:

$ cd /path/to/destination/directory
$ pushd /path/to/source/directory

# copy
cp -v 'files_to_copy.list' ~1

Veja também: esta seção da página man do Bash

Da mesma forma, no Tcsh, você pode usar a notação =2 (em vez de ~2 ) para se referir ao segundo diretório em sua pilha de diretórios.

Veja também: esta seção da página do manual do Tcsh

    
por 12.03.2016 / 00:07
4

quando você está no primeiro diretório, digamos que a fonte ou src em resumo, execute

src=${PWD}

depois cd para o segundo diretório e execute:

cp -i ${src}/filename .

a opção -i perguntará se você deseja sobrescrever, se houver um arquivo duplicado

    
por 10.03.2016 / 05:11
4

Uma variação na resposta de anderson-m-gomes. Usando o Bash, gostaria de visitar os diretórios:

$ cd /path/to/source/directory
$ cd /path/to/destination/directory

Então, eu usaria a variável $ OLDPWD, que aponta para o diretório anterior:

$ cp -v $OLDPWD/file1.txt .

Se alguém quiser visitar diretórios em ordem reversa, então:

$ cp -v fileA.txt $OLDPWD/
    
por 10.03.2016 / 14:41
2

Você pode usar xclip :

NAME
       xclip - command line interface to X selections (clipboard)

SYNOPSIS
       xclip [OPTION] [FILE]...

DESCRIPTION
       Reads  from standard in, or from one or more files, and makes the data available as an X selection for pasting
       into X applications. Prints current X selection to standard out.

Exemplo:

$ cd /path/to/dir1
$ xclip-copyfile file1 file2
$ cd /path/to/dir2
$ xclip-pastefile
file1 file2

Visite também xsel .

    
por 10.03.2016 / 11:12
2

Se no bash, eu usaria pushd e popd . Esses comandos mantêm uma pilha de diretórios FIFO à mão para uso posterior. Você pode consultar a pilha a qualquer momento usando dirs .

Como tal eu faria:

pushd .
cd /somewhere/else
cp "'popd'/myfile"
    
por 10.03.2016 / 08:12