2010-06-23 12 views
26

Posso impostare l'opzione predefinita di "Copia locale" in Visual Studio su False? Nella maggior parte dei casi, quando aggiungo una DLL come dipendenza di un progetto, voglio che la proprietà Copia locale sia impostata su False. Per impostazione predefinita, è True. C'è un modo per modificare il comportamento predefinito di Visual Studio? (2008)Imposta "Copia locale" su False per impostazione predefinita?

risposta

32

No - Visual Studio utilizza un set interno di regole per determinare a cosa impostare Copia locale.

Da MSDN:

  1. Se il riferimento è un altro progetto, chiamato un riferimento di progetto a progetto, allora il valore è vero .
  2. Se il gruppo si trova nella cache di assembly globale, il valore è falso.
  3. Come caso particolare, il valore del riferimento mscorlib.dll è falso.
  4. Se il gruppo si trova nella cartella Framework SDK, quindi il valore è falso.
  5. In caso contrario, il valore è true.
23

In realtà, è possibile. Avete bisogno di un paio di cose:

  1. Creare .targets di file che rende CopyLocal (<Private> tag, per la precisione) false by default.
  2. Importare il target nei file .csproj. Puoi aggiungerlo nell'ultima riga, prima di chiudere il tag </Project>, sembrerà <Import Project="..\Build\yourtarget.targets" />.

Ora ogni progetto con questo obiettivo è disattivato in modalità copilocale per impostazione predefinita.

Lo svantaggio è che è necessario modificare ogni singolo file csproj, inclusi quelli nuovi. Puoi risolvere il nuovo problema del progetto entro il modifying the VS project template. Invece di Class.cs descritto nell'articolo del blog, è necessario modificare Class.vstemplate (nello stesso file zip).

Con questo approccio, c'è un altro problema: il percorso stesso. Se si utilizza il percorso relativo hardcoded nei file csproj appena creati, potrebbero essere errati (a meno che non si abbia una struttura di progetto piatta).

È possibile:

  • Fai VS generare corretto percorso relativo. Non sei sicuro di come farlo e se è anche possibile.
  • Ignoralo e modifica il percorso manualmente per ogni nuovo csproj (a seconda del numero di nuovi progetti che hai, anche se non è l'ideale, che può essere tollerabile).
  • Utilizzare la variabile di ambiente anziché il percorso relativo. In tal caso, ogni sviluppatore avrà bisogno della stessa serie di variabili.

Ci deve essere una soluzione migliore per questo, ma non l'ho ancora trovato.

+0

Questa sembra essere la risposta corretta, ho seguito la guida ei collegamenti e funziona! –

+0

@AnthonyMastrean: hai trovato un modo intelligente per importare in un file csproj appena creato? – ya23

+0

Stiamo giocando con un file '.csproj' comune che viene importato in ogni nuovo progetto usando un modello. Il sistema dei template non è molto pulito e non siamo sicuri se ci piaccia ancora. –

5

Urtando questo perché sembra che ci sia ora un pacchetto NuGet consente esattamente questo ...

https://nuget.org/packages/CopyLocalFalse

non ho ancora provato, sperando solo aiuta.

+0

Con questo pacchetto di nuget non c'è alcuna garanzia. ha alcuni filtri predefiniti nello script di installazione che salteranno alcuni dei riferimenti, ma solo al momento dell'installazione del pacchetto nuget.Il pacchetto nuget potrebbe essere già installato e un nuovo riferimento aggiunto nel frattempo.Qualsiasi cosa se il pacchetto nuget viene ripristinato prima che altri pacchetti vengano ripristinati, quali altri pacchetti possono resettare copia locale dei loro assembly di riferimento? approccio non raccomandato. meglio usare un target per sovrascrivere la copia locale e avere il proprio fi ltraggio. – vezenkov

3

Non utilizzare un file .targets (come suggerito nella risposta da ya23), quindi dobbiamo solo modificare manualmente il file .csproj progetto in un editor di testo e aggiungere l'elemento <Private> al riferimento, in questo modo:

<Reference Include="[...]"> 
    <Private>False</Private> 
    [...] 
</Reference> 

Il valore dell'elemento <Private> corrisponde al valore della proprietà "Copia locale". Ad esempio, se <Private> è impostato su False, anche "Copia locale" è falso ..

0

Per quanto riguarda la soluzione inviata da @herzbube, se si desidera disattivare "Copia locale" per tutti (o la maggior parte) del riferimenti nel file csproj, non è necessario impostare <Private>False</Private> singolarmente su ogni Reference, si può semplicemente mettere il seguente direttamente nel csproj:

<ItemDefinitionGroup> 
    <Reference> 
    <Private>False</Private> 
    </Reference> 
</ItemDefinitionGroup> 

Questo non influenza i progetti di riferimento con <ProjectReference>, ma puoi fare la stessa cosa - sia invece che pure - per ose:

<ItemDefinitionGroup> 
    <ProjectReference> 
    <Private>False</Private> 
    </ProjectReference> 
</ItemDefinitionGroup> 

Se si desidera entrambe queste, è possibile unirli in un unico gruppo:

<ItemDefinitionGroup> 
    <Reference> 
    <Private>False</Private> 
    </Reference> 
    <ProjectReference> 
    <Private>False</Private> 
    </ProjectReference> 
</ItemDefinitionGroup> 

Assicurati di mettere degli scostamenti prima del primo vero e proprio <Reference ...> o <ProjectReference ...> si vuole influenzare perché questi blocchi si applicano solo a quei riferimenti che appaiono sotto di loro. Poi, se ci sono alcuni che si fai in realtà vogliono essere copiati localmente, si può semplicemente ignorare quelli indietro individuale (vale a dire, all'interno dell'individuo tag stesso), questa volta usando True.

Per i casi più avanzati è possibile passare il valore prioritario avanti e indietro tra Vero e False più volte nello stesso file Csproj. Un'altra tecnica avanzata sarebbe quella di posizionare strategicamente alcuni dei tuoi riferimenti sotto questi blocchi, e altri sopra, in modo che questi ultimi non ne risentano.

Tutto ciò dovrebbe rendere l'XML nel tuo .csproj molto più pulito e facile da leggere. Ma c'è ancora di più una buona notizia, quindi continuate a leggere ...


Per quanto riguarda la selezione cui i progetti dovrebbero essere essere contrassegnati <Private>False</Private> questo di solito dipenderà dalla situazione specifica, ma c'è qualcosa di fondamentale tutti può e dovrebbe do per i principianti. È un passo così semplice, semplice ed efficace e offre enormi miglioramenti di affidabilità MSBuild1. e costruire in tempo aumento di velocità - e con poco svantaggio - che ogni soluzione di grandi dimensioni che utilizza il default (cioè locale per ogni singolo progetto) C# posizioni di uscita dovrebbe quasi sempre eseguire questa regolazione:

In ogni e ogni soluzione Visual Studio che si basa più librerie di classi C# con qualsiasi numero non banale di <ProjectReference> interdipendenze, e che culmina nella costruzione di una più applicazioni (cioè eseguibili):

  1. Vicino alla parte superiore .csproj per ogni libreria di classi, inserire il blocco <ProjectReference> mostrato sopra.
    RAGIONE: Non è necessario alcun .dll per raccogliere una qualsiasi delle librerie a cui fa riferimento in una sottodirectory, poiché nessun file eseguibile viene mai eseguito da quella posizione. Tale copia sfrenata è inutile e potrebbe rallentare inutilmente la tua build, forse in modo piuttosto drammatico.

  2. D'altra parte, fanno non modificare il .csproj per una qualsiasi delle applicazioni del soluzione.
    REASON: gli eseguibili devono disporre di tutte le librerie private di cui hanno bisogno nelle rispettive sottodirectory, ma la build per ogni app da sola dovrebbe essere responsabile della raccolta individuale di ogni dipendenza, direttamente dalla rispettiva sottodirectory, nell'app sub-directory.

Questo funziona perfettamente perché il csproj per una libreria di classi possono fare riferimento a più altre librerie di classi, ma la Csproj per un eseguibile di solito non fa riferimento a un'altra eseguibile. Pertanto, per ogni libreria generata localmente, l'unica .dll nella sua cartella bin sarà essa stessa, mentre ogni applicazione generata a livello locale conterrà l'intera serie di librerie create localmente a cui fa riferimento.

Convenientemente, non cambia nulla per le librerie referenziate che non sono costruite dalla soluzione, poiché di solito usano <Reference> anziché <ProjectReference> e non abbiamo modificato affatto il tag precedente. Ma prendi nota dell'ipotesi appena menzionata; se viene violato da alcuni dei tuoi progetti, potrebbe essere necessario apportare alcune modifiche.

[1.] I miglioramenti dell'affidabilità potrebbero essere correlati alle collisioni di file che possono verificarsi quando si raccoglie la stessa libreria da più percorsi disgiunti in un grafico di dipendenza, in particolare nelle build simultanee.

Problemi correlati