Posso controllare la posizione delle impostazioni dell'utente .NET per evitare di perdere le impostazioni durante l'aggiornamento dell'applicazione?
Domanda
Sto cercando di personalizzare la posizione del file user.config
. Attualmente è memorizzato con un hash e un numero di versione
%AppData%\[CompanyName]\[ExeName]_Url_[some_hash]\[Version]\
Voglio che sia agnostico rispetto alla versione dell'applicazione
%AppData%\[CompanyName]\[ProductName]\
Questo può essere fatto e come? Quali sono le implicazioni? L'utente perderà le impostazioni della versione precedente dopo l'aggiornamento?
Soluzione
Per rispondere alla prima domanda, puoi tecnicamente posizionare il file dove vuoi, tuttavia dovrai codificarlo tu stesso, poiché il posto predefinito in cui si trova il file è il primo dei tuoi due esempi. ( link a come farlo da soli )
Per quanto riguarda la seconda domanda, dipende da come si distribuisce l'applicazione. Se si esegue la distribuzione tramite .msi, ci sono due hash nelle proprietà del progetto di installazione (da cui è stata creata la msi), il "codice di aggiornamento" e il "codice prodotto". Questi determinano come installare l'MSI e se si aggiorna, sovrascrive o si installa accanto a qualsiasi altra versione della stessa applicazione.
Ad esempio, se hai due versioni del tuo software e hanno codici di 'upgrade' diversi, allora per Windows sono software completamente diversi indipendentemente dal nome. Tuttavia, se il codice "upgrade" è lo stesso, ma il codice "product" è diverso, quando si tenta di installare il 2o msi ti verrà chiesto se si desidera eseguire l'aggiornamento, a quel punto si suppone che copi i valori dal vecchia configurazione in una nuova configurazione. Se entrambi i valori sono uguali e il numero di versione non è cambiato, la nuova configurazione sarà nella stessa posizione della vecchia configurazione e non dovrà fare nulla. Documentazione MSDN
ClickOnce è un po 'diverso, perché si basa più sul numero di versione ClickOnce e sul percorso URL, tuttavia ho scoperto che finché continui a "Pubblicare" nella stessa posizione, la nuova versione dell'applicazione continuerà per utilizzare la configurazione esistente. ( link al modo in cui ClickOnce gestisce gli aggiornamenti )
So anche che esiste un modo per unire manualmente le configurazioni durante l'installazione di msi usando script di installazione personalizzati, ma non ricordo i passaggi esatti per farlo ... (vedi questo link per come farlo con un web.config)
Altri suggerimenti
Volevo aggiungere questo testo citato come riferimento per quando avrò questo problema in futuro. Presumibilmente è possibile indicare all'infrastruttura di ApplicationSettings di copiare le impostazioni da una versione precedente chiamando Aggiorna :
Properties.Settings.Value.Upgrade();
Da Domande frequenti sulle impostazioni client post sul blog: ( archivio )
D: Perché c'è un numero di versione nel percorso user.config? Se distribuisco una nuova versione della mia applicazione, l'utente non perderà tutte le impostazioni salvate dalla versione precedente?
A: Ci sono un paio di ragioni per cui il file Il percorso user.config è sensibile alla versione.
(1) Per supportare la distribuzione side-by-side di diverse versioni di un applicazione (puoi farlo con Clickonce, per esempio). È possibile per diverse versioni di applicazione per avere impostazioni diverse salvato.
(2) Quando si aggiorna un applicazione, la classe delle impostazioni può sono stati modificati e potrebbero non esserlo compatibile con ciò che è salvato, che può portare a problemi.
Tuttavia, l'abbiamo reso semplice aggiorna le impostazioni da una precedente versione dell'applicazione al più recente. Chiama semplicemente ApplicationSettingsBase.Upgrade () e recupererà le impostazioni da versione precedente che corrisponde al versione corrente della classe e del negozio li fuori nella versione corrente file user.config. Hai anche il possibilità di ignorare questo comportamento nella classe delle impostazioni o in l'implementazione del tuo provider.
D: Okay, ma come faccio a sapere quando chiamare Upgrade?
A: Buona domanda. In Clickonce, quando installi una nuova versione del tuo applicazione, ApplicationSettingsBase lo rileverà e automaticamente aggiorna le impostazioni per te al punto le impostazioni sono caricate. In non Clickonce casi, non esiste un aggiornamento automatico - devi chiamare Aggiorna te stesso. Ecco un'idea per determinare quando per chiamare Upgrade:
Richiama un'impostazione booleana CallUpgrade e impostalo come predefinito valore di vero. All'avvio dell'app in alto, puoi fare qualcosa del tipo:
if (Properties.Settings.Value.CallUpgrade)
{
Properties.Settings.Value.Upgrade();
Properties.Settings.Value.CallUpgrade = false;
}
Questo assicurerà che Upgrade () sia chiamato solo la prima volta il l'applicazione viene eseguita dopo una nuova versione è distribuito.
Non credo per un secondo che potrebbe effettivamente funzionare - non c'è modo che Microsoft possa fornire questa capacità, ma il metodo è lo stesso.
Il file user.config è archiviato in
c:\Documents and Settings>\<username>\[Local Settings\]Application Data\<companyname>\<appdomainname>_<eid>_<hash>\<verison>
<c:\Documents and Settings>
è la directory dei dati dell'utente, non in roaming (Impostazioni locali sopra) o in roaming.
<username>
è il nome utente.
<companyname>
è il valore CompanyNameAttribute, se disponibile. Altrimenti, ignora questo elemento.
<appdomainname>
è AppDomain.CurrentDomain.FriendlyName. In genere, il nome predefinito è .exe.
<eid>
è l'URL, StrongName o Path, basato sulle prove disponibili per l'hash.
<hash>
è un hash SHA1 di prove raccolte da CurrentDomain, nel seguente ordine di preferenza:
1. StrongName
2. URL:
Se nessuno di questi è disponibile, utilizzare il percorso .exe.
<version>
è l'impostazione AssemblyVersionAttribute di AssemblyInfo.
La descrizione completa è qui http://msdn.microsoft.com/en-us/library /ms379611.aspx
(Aggiungo questo come commento alla risposta di @ Amr, ma non ho ancora abbastanza rappresentante per farlo.)
Le informazioni nell'articolo MSDN sono molto chiare e sembrano ancora applicare. Tuttavia non menziona il fatto che l'hash SHA1 è scritto con codifica base 32, piuttosto che con la base più tipica 16.
Credo che l'algoritmo utilizzato sia implementato in ToBase32StringSuitableForDirName
, che può essere trovato qui nell'origine di riferimento di Microsoft .