Git Mirror with Different Branches - android

I am working on Android Source Code, and I used mirror to let the time of sync faster.
$ mkdir mirror
$ cd mirror
$ repo init branchA --mirror
$ repo sync
Then, I can use this mirror when I need to sync branchA each time.
$ repo init branchA --reference=/.../mirror
$ repo sync
But now, I have a question, I have other branches which are related to branchA. For instance, branchB is based on branchA, and banchC is based on branchB. In this case, should I need three different mirror ?
If I only sync branchC's mirror, Can I use this mirror to sync branchA and branchB ?
If I only sync branchA's mirror, Can I use this mirror to sync branchB and branchC ?

You need only one mirror.
Repo's mirror repositories are fully cloned. They contain every git object reachable from all the branches, tags and other refs. repo sync's option -c, which downloads only the current ref and its objects, will take no effect in mirror repositories.
Even if the mirror has only one branch's data, you can still use it as reference to download other refs. The missing refs and objects, which can't be found in the mirror, will be downloaded from the remote server. You won't miss anything in the working repositories.

Related

Different git repo for Configure Build Variants

I have an app with different version.
But every version have different Git repository.
So please let me know how we can manage that every build variant have different repository.
You should have different tags or branches per version, not different repositories.
From the same repo, you would then use git worktree in order to clone the repo once, but checkout the repo multiple times: see "Multiple working directories with Git?".
That way, you have different folders, each one with a different version of your project.
Since only the name/color/logo are changing, you would need:
one repo with all the common code
one configuration file with the right values for name/color/logo per environment
one way for your code to detect in which environment it is deployed: your code you then pick the right value from the config file.
The point is: one project, one Git repo: See the 12 factors app (in particular, the Config section).

What is the mechanism of GIT merging?

I'm novice learner of GIT. i'm developing a social networking app. with a friend on Android which is a significantly massive project, so in order to synchronize our development, i decided to use Version Controlling. Now my project is on BitBucket. i'm decided not to waste time on command line and started using "SourceTree" to manage. Now i've certain confusion. i understand the fundamentals of Commits, push , fetch , branching etc. My question is :
Lets say, both me and my friend are working on different activities in our development branches of app. and making commits , but there are some files common to us , like Manifest.xml , build.gradle etc.. so when these branches are merged to "Production/Master" , how will the changes in these "common" files will get accommodated ? what if we both added code to a certain file and arrangement of lines of code matters , then how the merging mechanism will gives us a working project with integrated modules , if i'm wrong with my basic concepts, feel free to correct and suggest me some reference material. thanks in advance
When the same file is being modified in two different instance and then merges, there are two possible outcomes. If the code that is modified in in the files are in different sections, Git will merge the two files. If both files modify the same section of the code then Git will give you a merge conflict, which you will then have to resolve.
The following link goes over the details of resolving merge conflicts.
https://help.github.com/articles/resolving-a-merge-conflict-from-the-command-line/
Another option that should be looked at is rebasing.
https://www.atlassian.com/git/tutorials/merging-vs-rebasing/conceptual-overview
If you and your friend modify the same file. When you do the merge could happen 2 things:
If both of you modify the same file in different regions of code. Git is capable to do the merge without conflicts.
If both of you modify the same file in the same regions of code. Git will do the merge with conflicts.
If the file has conflicts, it will looks like this:
... Some code ...
<<<<<<< HEAD
Line added by you
-------
Line added by your friend
>>>>>>> branch_name
... More code ...
You need to decide which of the two lines (Line added by you and line added by your friend) has the correct code. Then, delete the line that has the wrong code and the following lines:
<<<<<<< HEAD
-------
>>>>>>> branch_name
If you want, you can setup a tool to resolve conflicts like p4merge. You can download it from:
p4merge for Windows 64 bits
p4merge for Windows 32 bits
p4merge for other OS
You install this tool and then you need to setup with this git commands:
git config --global mergetool.p4merge.path 'C:\Program Files\Perforce\p4merge.exe'
git config --global merge.tool p4merge
To verify if all is right. Your .gitconfig file (C:\Users\windows_user\.gitconfig) will look like this:
[merge]
tool = p4merge
[mergetool "p4merge"]
path = C:\\Program Files\\Perforce\\p4merge.exe
After you have run the git merge command. To resolve conflicts using p4merge, you need to execute the git mergetool command. It opens the p4merge tool and show the conflicts like this image:
Merges are done via a couple of different mechanisms. The default usually works well, particularly for smaller teams. When things get larger then one of the other algorithms can be more effective. If there are areas touched by both parties, they are flagged as conflicts and you must manually resolve. I suggest reading the Git book for more details and examples:
https://git-scm.com/book/en/v2/Git-Branching-Basic-Branching-and-Merging

Create Android server local repository for specific tag

I would like to create a local server for Android branch android-4.3_r1.1
I follow this thread:
Cloning Android sources to a local repository server
But I couldn't do the same thing for specific tag,
How can it be done ?
I would like to have a server, and then from the client do some work and push it to the server, so other client can do a sync and see my commits ...
On the server side this is what I did:
repo init -u https://android.googlesource.com/platform/manifest --mirror
repo sync
On the client side:
repo init -u git-server/android/platform/manifest.git/ -b android-4.3_r1.1
repo sync
I get many of some kind of these errors:
fatal: 'git-server/android/device/ti/panda' does not appear to be a git repository
fatal: The remote end hung up unexpectedly
And all the process is failed ... (error: Exited sync due to fetch errors)
I would like a client AOSP working on android-4.3_r1.1 then do some changes and commit them to the git server.
The repo init --mirror -u $URL/platform/manifest method is sane, but you'll only sync the gits listed in the manifest in question (the master branch, in this example). So, while all gits that are synced will contain all branches and tags needed, the manifest itself doesn't include all gits so subsequent attempts to initialize workspaces based on the created mirror will fail if the manifest branch you've chosen to sync points to gits not included in the master branch's manifest.
The AOSP team has set up special manifest, mirror/manifest, that isn't useful for building anything but lists all gits from all branches and therefore is highly useful for mirroring. In other words, initialize your mirror like this:
repo init --mirror -u https://android.googlesource.com/mirror/manifest
See the AOSP Downloading the Source documentation.

Reproducible android builds with git with fast forward merges

I'm looking reproducibility between android system (AOSP) daily builds against repo's collections of git repositories and the impact of using fast-forward merges.
The problem is that when doing daily builds you will get a tip-of-tree while development is happening elsewhere. If HEAD hasn't changed when the change is pushed, it will do a fast-forward merge and time will be re-written. So effectively the physical state of the repository 3 days ago will be different than asking git to go back three days.
The prime solution I can see is to use git with --no-ff to force merge commits. This injects a lot of noise for smaller commits, and seems to be considered bad practice in keeping a clean tree.
The background on this is trying to have reproducibility in an android build environment. For those that don't know, an android build is a collection of disparate git repositories. My ultimate use case is that I want to be able to say, put the code base in the state it was for developers 3 days ago. With fast-forward merges, we lose some critical information on how to correlate between changes on multiple repo projects (ie: git repositories).
As you've noticed, Git doesn't track the state of a branch over time. Two reasonable options are to either set tags for each build or to create a static manifest with the SHA-1s of all checked out commits at the time of the build:
repo manifest -r -o build_20131104.xml
Those files can either be checked into the manifest git and used like e.g.
repo init -u ... -m build_20131104.xml
to reproduce the prior state or you can save the files elsewhere.
Tagging all the gits litters the tag namespace if you're doing a lot of builds (and Git is currently fairly slow with thousands of tags) but is otherwise pretty convenient. Don't forget to tag the manifest git too.

Cloning Android sources to a local repository server

I want to develop on top of Android using a local Android repository server. I need to add several new git repositories to the hierarchy of gits, and I need to modify existing android sources for a custom tailoring of Android.
What is the "correct" way to clone the entire Android source tree of git repositories, such that I can push/pull to/from a common local repository server, and still easily pull new changes from Android upstream?
I am specifically looking for advice on how to use the repo script for interaction with my own server, and how to set up the manifest git repository and managing branches therein.
On your git server
repo init -u https://android.googlesource.com/platform/manifest --mirror # --mirror is the key
repo sync
Because you specified --mirror, all repos created will be 'bare' repos, which is the git-correct way to create a mirror unless you are a git uberlord.
On your client:
repo init -u git#git.yourserver.com:platform/manifest.git # you may use a different means of accessing your git server; I have to assume something for this example.
no repo sync yet. Your manifest is probably wrong. Look at the symbolic linked .repo/manifest.xml... cat it and read at the top the <remote fetch=""... it probably points back to android.googlesource.com. but if it says '..' I think that means 'come back to my server', so you can skip to step 6). But if it does point back to another server (not yours), then go to step 3.
cd .repo/manifests
vim .repo/manifests/default.xml (or whatever your active manifest.xml is).
Fix default.xml's <remote fetch="CHANGE ME" to point back to your git server
attempt a repo sync. It should pull only from your repository. If it doesn't, stop the repo sync, and try to fix default.xml again.
Once you see repo sync work on your test machine, then commit default.xml back in (git commit; git push), so that others on the team will have 'no-manifest-edit' experience when they repo init; repo sync from your server.
Once you see a 'no manifest edit' repo init; repo sync work, then go to your default.xml again, and just start adding new XML elements along with the tons of other existing Android project elements; these new elements will point to your custom projects. For these new projects, just git init them as you normally would, and make sure they have a branch matching the same <default revision="whatever_branch_you_see_here" so that a repo sync will succeed when it encounters these new projects.
If you do indeed set a default branch in your manifest <default revision="" element, then just have everyone make a local branch set to follow the remote branch specified in the revision attribute. So, for example, if <default revision="branch_a" is in your manifest, after you do a repo sync, when you cd into a sub-project of interest, do a :
git checkout -b branch_a origin/branch_a
Then, if the user git push's (there is no repo command to push, as far as I'm aware), and if someone else does a ./repo sync after that push, they will get those changes from the original user... as long as you are using the same manifest and actually pushing to the default revision (branch) specified by that manifest.
That's the simplest recipe. If you want to make actual feature branches, then you'll have to edit your manifest more regularly if you want 'repo sync' to just work... and you will have to communicate to the rest of the team to grab your version of the manifest when you do that. Alternatively, if it's just one or two git repos you are touching, then you could just forego repo sync and git push/pull like normal on those repos and ignore the rest of the quiet tree for the times you are heavily iterating. This sounds, ultimately to me, like a simpler path. I'd ignore repo as much as you possibly can; only using it for 'all project' syncs and leaving it alone for the times you are focusing on 1 or 2 projects.
Regarding getting updates from upstream. I think the way to do that is to change your default.xml to point back to your original git location (like android.googlesource.com), do a repo sync to cause all the new stuff to merge in, and once done with the sync, commit back up to your repo. I haven't done this yet; so I can't be too specific, but this is how I plan to do it.
I'm ignoring server administration details above. For instance, you need to call the repo init in a certain directory on your git server to cause it to be an available git repository; I'm assuming you know how to administer your git server.

Categories

Resources