Xcode modifica storyboard e file XIB non modificati


132

Gli storyboard sono piuttosto una sofferenza reale dal punto di vista del flusso di lavoro git quando più persone collaborano su di essi. Ad esempio, l'XML nel file .storyboard ha i suoi <document>tag di partenza toolsVersione gli systemVersionattributi modificati da qualunque configurazione sia in esecuzione il manipolatore di file più recente. Sincronizzare con precisione le versioni di Xcode di tutti sembra aiutare toolsVersion, ma systemVersioncambia qualunque cosa, a seconda della specifica versione di Mac e / o OS X che lo sviluppatore sta eseguendo.

Questo è idiota, ma per lo più innocuo. Ciò che ci preoccupa, tuttavia, è che altre volte vengono apportate automaticamente altre modifiche allo storyboard semplicemente aprendole dopo un git pull. Vale a dire, Alice apporta modifiche allo storyboard, si impegna e le inserisce nel repository. Bob quindi tira le modifiche di Alice e apre lo storyboard per apportare ulteriori modifiche. Nel momento in cui apre lo storyboard, l'icona del file cambia immediatamente in uno stato modificato ma non salvato, e git statusmostra che si è verificato un numero qualsiasi di strani cambiamenti. Tutto questo senza che Bob abbia cambiato nulla o salvato il file da solo.

Il cambiamento automatico più comune che stiamo vedendo è la scomparsa o la ricomparsa dell'intera <classes>gerarchia dei tag vicino alla fine di un file dello storyboard. Non abbiamo capito cosa sta causando questo. Potremmo avere diverse versioni localizzate di uno storyboard in varie directory .lproj e quando le si apre in Interface Builder, la gerarchia di classi può essere spontaneamente rimossa da alcune e aggiunta ad altre o lasciata sola in alcune. Ciò provoca molto rumore git diff, ma in realtà non interrompe alcuna funzionalità. Aggiungiamo spesso in modo selettivo le modifiche effettive apportate all'indice di Git, le commettiamo e quindi scartiamo il spontaneo, senza senso<classes>i cambiamenti. Questo per mantenere gli impegni piccoli e carini, come dovrebbero essere. Alla fine, però, diventa troppo preoccuparsi poiché Xcode continua a ripetere le modifiche, e qualcuno le consiglia semplicemente insieme ad altre cose ... il che va bene fino a quando l'Xcode di qualcun altro non decide di volerle cambiare di nuovo per no ragione apparente. (La nostra cronologia degli impegni ha parecchie imprecazioni.)

Qualcun altro vede questo comportamento? Si tratta di un bug Xcode o di un problema di configurazione su uno o più Mac per sviluppatori? Abbiamo visto un comportamento simile durante la collaborazione con i file XIB, ma gli storyboard sembrano più sensibili a questo.


In effetti i progetti Xcode e Git non stanno andando molto bene insieme. Non penso che tu possa evitare questo pasticcio in modo diverso da scartare le modifiche che non sono necessarie - che sono quasi sempre le modifiche ai file di progetto per me e altri file xml Sono sicuro di non aver cambiato. Saremo felici se ci sarà una sorta di "soluzione". Mi piace Perforce per la comoda funzionalità di blocco che non consente a Xcode di cambiare troppo, che probabilmente potrebbe essere fatto manualmente per i file che non hai intenzione di cambiare ma solo per rivedere.
A-Live

3
Non vale la pena usare gli storyboard con git o altro. Non sono progettati per essere facili da commettere. Ci siamo arresi e siamo andati con .xib che non è poi così eccezionale, ma almeno è granulare.
Ahwulf

Abbiamo trovato gli storyboard piuttosto belli per molte cose in realtà, anche se spesso è necessario mescolarli con gli XIB. Se questo bug viene mai risolto, saremmo abbastanza felici di lavorare con loro nella stragrande maggioranza delle volte.
JK Laiho,

Devo solo commentare il commento di ahwulf: cosa diavolo intendi che non sono amichevoli? Sono file XML / di testo, questo è il più facile da impegnare che puoi ottenere. E ho avuto 'nessun' problema con lo storyboard e un sistema di versioning, l'unico problema è ovviamente che xcode a volte elimina il tag <classes> e poi lo legge più tardi, ma puoi vederlo facilmente se guardi i cambiamenti con una GUI git o git -p o equivalente per qualunque dvcs. Non ho mai avuto questo accadere con il file .pbxproj come un file.
mgrandi,

Non riesco a capire perché xcode inserisca i blocchi di classi nello storyboard se riesce a generare quei blocchi semplicemente leggendo i file delle classi? sono una sorta di "cache"? in tal caso dovrebbero essere inseriti in un file classes.cache in modo da poterlo escludere dal controllo delle versioni ...
hariseldon78,

Risposte:


78

Questo non è un bug, è una conseguenza di come Xcode elabora i file dello storyboard. Sto scrivendo un programma diff e merge per i file dello storyboard (collegamento GitHub) e ho trascorso ore ad analizzare la logica dei file dello storyboard e il modo in cui Xcode la elabora. Questo è quello che ho scoperto:

  • Perché si verificano strani cambiamenti nei file dello storyboard? Xcode utilizza l'API NSXML per analizzare i file dello storyboard in una NSSetstruttura ad albero logico basata su. Quando Xcode deve scrivere le modifiche, ne crea una NSXMLDocumentbasata sulla struttura ad albero logico, cancella il file dello storyboard e chiama XMLDataWithOptions:per riempire nuovamente il file. Poiché i set non conservano l'ordine dei loro elementi, anche la minima modifica potrebbe cambiare l'intero file XML dello storyboard.

  • Perché il tag di classe scompare o riappare in modo casuale? La <class>sezione non è altro che una cache Xcode interna. Xcode lo usa per memorizzare nella cache informazioni sulle classi. La cache cambia spesso. Gli elementi vengono aggiunti quando i .h/.mfile di classe vengono aperti e rimossi quando Xcode sospetta che siano obsoleti (almeno gli Xcodes precedenti si comportano in questo modo). Quando si salva lo storyboard, viene scaricata la versione corrente della cache, motivo per cui la <class>sezione spesso cambia o scompare.

Non ho Xcode retroingegnerizzato; Ho fatto queste osservazioni sperimentando file Xcode e storyboard. Tuttavia, sono quasi sicuro al 100% che funzioni in questo modo.

Conclusioni :

  • La sezione cache non è importante; puoi tranquillamente ignorare qualsiasi cambiamento in esso.
  • Contrariamente a quanto puoi trovare su tutti i forum, la fusione dei file degli storyboard non è un compito complicato. Ad esempio, supponiamo che tu abbia cambiato il MyController1controller di visualizzazione in un documento storyboard. Apri il file dello storyboard e trova qualcosa del genere <viewController id=”ory-XY-OBM” sceneMemberID=”MyController1”>. Puoi confermare in sicurezza solo le modifiche in questa sezione e ignorare tutto il resto. Se hai modificato segues o vincoli, commetti anche tutto ciò che ha “ory-XY-OBM”dentro. Semplice!

9
Qualche aggiornamento sullo strumento diff / mer xcode? Sembra che sarà super utile per questa community.
Tony,

1
È possibile ottenere l'app dalla mia pagina Web (vedi profilo). L'app è gratuita al 100%.
Marcin Olawski,

1
Per me suddividere gli storyboard il più possibile == usando gli XIB. Se vuoi avere tutto affettato, è più facile e meglio usare gli XIB
Marcin Olawski,

7
"Non ho retroingegnerizzato Xcode; ho fatto queste osservazioni sperimentando i file Xcode e storyboard." Questo è (superficiale) reverse-engineering, ed è fresco . :-)
Constantino Tsarouhas,

13
"Questo non è un bug, è una conseguenza di come Xcode elabora i file dello storyboard." Rispettivamente, la seconda metà di questa frase non spiega in alcun modo né razionalizza la prima. Lo modificherei in: "Questo è un bug. È una conseguenza [n purtroppo irrisolta e molto fastidiosa] di come XCode elabora i file .xib". Da XCode 5.x a 6.2 (oggi 150311) i file .xib non sono stati in alcun modo modificati dallo sviluppatore, semplicemente visualizzati in IB, subiscono modifiche XML gratuite. Questo è un grosso errore che influisce sulla produttività. Le risposte come "NBD, basta trattare con pezzi di git" mi lasciano senza parole.
circa il

18

Questo è un bug in XCode 4.5+, spero che venga corretto, e sì, è un PITA.

Ecco il bug completo di Apple

Come evitare le modifiche gratuite di Xcode ai file dello storyboard?


1
Stessa cosa in 4.6. Forse non è un bug.
Thromordyn,

4.6.3 ce l'ha ancora. Non posso dire che lo storyboard / xibs abbia mai funzionato bene però
houbysoft il

1
"Non è un bug, è una caratteristica": -S
MrTJ

Non ci sono prove che si tratti di un bug - un fastidio sì, ma potrebbe essere solo il modo in cui Xcode fa cose
Thomas Watson

1
7.0.1 non ha apportato modifiche a questo.
Andris Zalitis,

11

Questo problema può essere mitigato in qualche modo da un uso estremamente giudizioso di git add -pqualsiasi file generato da Xcode, inclusi storyboard, XIB, modelli di dati core e file di progetto, che soffrono tutti di modifiche transitorie simili che non hanno alcun impatto sull'interfaccia / modello / progetto.

Le modifiche indesiderate più comuni che ho visto sugli storyboard sono i numeri di versione del sistema (come dici tu) e la costante aggiunta e rimozione della <classes>sezione, la cui omissione non ho mai visto causare problemi. Per gli XIB, è l'aggiunta e la rimozione di <reference key="NSWindow"/>, che non è nemmeno una classe in Cocoa Touch. Wow.

Pensalo come il mare: c'è sia un'alta che una bassa marea. Lascia che ti lavi sopra.

Ahh. Questo è tutto.

È possibile ignorare queste modifiche durante la messa in scena delle modifiche, reimpostare le modifiche indesiderate ed eseguire un commit pulito.

L'unico vantaggio che ho riscontrato con gli storyboard sugli XIB dal punto di vista tecnico è che Apple non ha ancora sterilizzato FileMerge per rifiutare di unire gli storyboard in conflitto. (FileMerge era in grado di unire gli XIB, ma le versioni più recenti lo hanno rotto. Thxxxx ragazzi 💜 !!!)

Si prega di presentare molti bug su tutti questi problemi su http://bugreporter.apple.com/ ! E non dimenticare di creare voci su OpenRadar .


6

Dare un'altra risposta qui perché questa situazione è notevolmente migliorata. L'XML per il file XIB che rappresenta lo StoryBoard è stato notevolmente semplificato.

Recentemente ho anche morso il proiettile e ho iniziato a utilizzare l'interfaccia in Xcode per il controllo del codice sorgente. Sono stato sulla riga di comando per anni e felice lì, ma l'interfaccia è carina e ti consente di dividere i commit, il che è molto importante se usi un sistema di ticketing che si collega ai commit.

Comunque, ho notato oggi che c'è stato un cambiamento nello storyboard e il diff integrato mi ha mostrato che era un singolo attributo nel tag del documento (systemVersion). Quindi non è un grosso problema.

Ho letto articoli in cui la gente dice che gli SB sono stati messi fuorilegge nei loro team a causa di problemi di fusione. Follia totale. Sono così straordinari, specialmente ora che hanno un autolayout intelligente integrato, ti stai davvero perdendo se non li stai usando.


3

È utile sapere perché sta accadendo questa follia, ma per coloro che credono nel mantenere i loro progetti liberi da avvertimenti e che vogliono solo un semplice e sporco per riportare i loro progetti in uno stato sano:

  1. Non commettere nulla fino a quando non viene esplicitamente indicato.

  2. Apri Xcode e crea un nuovo storyboard (Comando + N> iOS> Interfaccia utente> Storyboard). Presumo che tu lo chiami il nome predefinito di Storyboard.storyboard.

  3. Apri lo storyboard che Xcode ha violato. Suppongo che sia così Base.lproj/Main.storyboard.

  4. Seleziona e copia tutto sullo storyboard (Comando + A quindi Comando + C).

  5. Aprire Storyboard.storyboard.

  6. Copia e incolla tutto in Storyboard.storyboard.

  7. Chiudi Xcode.

  8. Apri un terminale e modifica le directory nel tuo repository.

  9. Sostituisci Main.storyboardcon Storyboard.storyboard( mv Storyboard.storyboard Base.lproj/Main.storyboard).

  10. git add Base.lproj/Main.storyboard; git commit -m "Fix Xcode's insanity."

  11. Ignorare le modifiche a project.pbxprojvia git checkout -- project.pbxproj. Se sei git diffil file, vedrai che ha appena aggiunto informazioni sul nostro storyboard temporaneo (che non esiste più).

  12. Apri Xcode back up e verifica che gli avvisi siano scomparsi.

  13. Respirare.


0

Lavorare sullo stesso storyboard non è un problema. Ma lavorare sullo stesso viewcontroller che crea conflitti in pull / merge è spaventoso. non possiamo davvero evitare di lavorare nello stesso viewcontroller per una grande squadra.

La cosa buona è che la maggior parte delle volte possiamo correggere gli stessi conflitti del viewcontroller se comprendiamo la struttura xml. Non ho mai fallito nel fonderli mentre lavoravo in gruppo. Supponiamo che tu stia lavorando con un viewcontroller. La tua vista è vuota al momento. Dai un'occhiata alla struttura XML del viewcontroller dall'opzione del codice sorgente.

inserisci qui la descrizione dell'immagine

Lo storyboard è xml delimitato dal tag del tipo di documento. Tutto nello storyboard contiene nella scena sceneID = tag. il tag scene contiene tutti i viewcontroller. Questo è quello di base.

Ora abbiamo aggiunto un UILabel e un UIButton alla vista. Imposta anche il layout automatico degli elementi. Ora sembra che:

inserisci qui la descrizione dell'immagine

L'aggiunta di un pulsante / livello al viewcontroller ha aggiunto un nuovo codice all'interno del tag subview della vista. La stessa cosa andrà per ulteriori aggiunte di elementi o eventuali modifiche dell'interfaccia utente. Controlla attentamente la struttura del tag che è davvero importante per correggere eventuali conflitti.

Ora aggiungiamo un altro viewcontroller nel nome dello storyboard Homeviewcontroller. L'aggiunta di un nuovo viewcontroller significa che aggiunge una nuova scena sotto il tag scene. Guarda questo:

inserisci qui la descrizione dell'immagine

A questo punto, cambieremo la struttura in modo casuale e osserveremo i problemi / avvertimenti. Modifichiamo il primo tag di fine etichetta viewcontroller e salviamo il file. Ora eseguilo e guarda l'avvertimento. L'errore indica che il tag di fine non è corretto, creato dalla riga 23. Nella riga 23, vediamo che i vincoli di un'etichetta sono impostati senza tag di fine. Questo è il problema. Ora inseriamo il tag end e costruiamo il progetto. Dopo aver impostato il tag di fine, possiamo visualizzare lo storyboard correttamente.

inserisci qui la descrizione dell'immagine

Di fronte a qualsiasi avviso di conflitto, si prega di confrontare con la fonte precedente e cambia fonte. Rimuoviamo il vecchio codice / ridondante, manteniamo il nuovo codice con il tag corretto inizio-fine e sistemiamo le cose.

[NB, aggiornerò la risposta con alcuni altri casi di test quando avrò i tempi]

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.