esr-rim 1.1.5 → 1.2.0
Sign up to get free protection for your applications and to get access to all the features.
- data/CHANGELOG +29 -0
- data/README.md +181 -0
- data/lib/rim/command/sync.rb +15 -3
- data/lib/rim/command_helper.rb +29 -14
- data/lib/rim/dirty_check.rb +1 -1
- data/lib/rim/module_helper.rb +4 -2
- data/lib/rim/module_info.rb +5 -0
- data/lib/rim/processor.rb +12 -0
- data/lib/rim/rim_info.rb +7 -5
- data/lib/rim/sync_helper.rb +33 -6
- data/lib/rim/sync_module_helper.rb +4 -19
- data/lib/rim/version.rb +1 -1
- data/test/rim_info_test.rb +3 -1
- metadata +13 -9
- checksums.yaml +0 -7
data/CHANGELOG
CHANGED
@@ -38,3 +38,32 @@
|
|
38
38
|
* added --gerrit option, needed for pushing new branchs to gerrit [BS-202]
|
39
39
|
* fixed exception on rim sync after moving working copy [BS-248]
|
40
40
|
|
41
|
+
# 1.1.1
|
42
|
+
|
43
|
+
* fixed rim sync fails if CRLF warning is present [BS-281]
|
44
|
+
* fixed rim upload fails to upload claiming branch does not exist [BS-264]
|
45
|
+
|
46
|
+
# 1.1.2
|
47
|
+
|
48
|
+
* fixed Exception in rim sync when autocrlf is turned on [BS-233]
|
49
|
+
|
50
|
+
# 1.1.3
|
51
|
+
|
52
|
+
* added -n (no review) option to rim upload.
|
53
|
+
* fixed rim sync doesn't handle filename case changes correctly [BS-254]
|
54
|
+
* made preparation of mirrored workspace more robust
|
55
|
+
|
56
|
+
# 1.1.4
|
57
|
+
|
58
|
+
* allow sync and upload on touched git working repository.
|
59
|
+
|
60
|
+
# 1.1.5
|
61
|
+
|
62
|
+
* fixed workaround for windows file lock problem [BS-308]
|
63
|
+
|
64
|
+
# 1.2.0
|
65
|
+
|
66
|
+
* changed commit strategy for sync to automatic squashing to a single commit. Added -s option to force separate commits.
|
67
|
+
* added -a option to allow simple specification of multiple syncs.
|
68
|
+
* added -r option that allows sync and rebase in one step [BS-319]
|
69
|
+
* fixed exception in rim sync when -u option is not provided [BS-232]
|
data/README.md
CHANGED
@@ -1,3 +1,184 @@
|
|
1
1
|
# RIM - Multi git tool
|
2
2
|
|
3
3
|
RIM lets you work with multiple git repositories from within one single git repository.
|
4
|
+
|
5
|
+
# RIM User Guide
|
6
|
+
|
7
|
+
> From RIM version 1.1.4 it is no more necessary to set the global git autocrlf option to false on Windows platforms. If you don't have other reasons you might want to set it back to the recommended value (which is true).
|
8
|
+
|
9
|
+
## Concept
|
10
|
+
|
11
|
+
RIM is used to synchronize software modules (let's call them library modules) which are git repositories into a project specific git repository. As long as you don't need to upgrade or modify one of the synchronized library modules, you don't need RIM. In other words: if somebody else in the project takes care of the library module synchronization, you can work with one single GIT repository without worrying about RIM or library module synchronization.
|
12
|
+
When RIM has synchronized a specific version of a library module into your project GIT, it records the source of the library module in the local module directory within a .riminfo file.
|
13
|
+
|
14
|
+
## Use Cases
|
15
|
+
|
16
|
+
* Check the status of your local commits (dirty or clean), which lists dirty modules just in case (rim status -d)
|
17
|
+
* Add a new library module to your project git (rim sync -c)
|
18
|
+
* Upgrade an existing library module (rim sync)
|
19
|
+
* Upload modifications of a library module (rim upload)
|
20
|
+
|
21
|
+
## Terms
|
22
|
+
|
23
|
+
* __Project__: a set of modules plus project specific code
|
24
|
+
* __Project Git__: a single git repository which contains all code belonging to the project (including the code from modules)
|
25
|
+
* __Module__: a unit of code which can be added to a project individually
|
26
|
+
* __Module Git__: git repository holding a module
|
27
|
+
* __Module Dir__: directory in the project workspace where the module is located
|
28
|
+
* __.riminfo File__: file contained in a Module Dir holding rim specific information
|
29
|
+
* __.rim Dir__: directory in a project root dir holding rim specific information
|
30
|
+
|
31
|
+
## Installation
|
32
|
+
|
33
|
+
Install and update RIM via the gem package mechanism:
|
34
|
+
|
35
|
+
> gem install esr-rim
|
36
|
+
|
37
|
+
## Getting started in your project
|
38
|
+
|
39
|
+
There's not a lot you have to do to introduce rim into your project. The most important step is:
|
40
|
+
Before using rim add the pattern
|
41
|
+
|
42
|
+
.rim/
|
43
|
+
|
44
|
+
to your project's `.gitignore` and commit this change.
|
45
|
+
|
46
|
+
## Synchronize your project git with a module git
|
47
|
+
|
48
|
+
Whenever you decide to use rim to synchronize the content of a library module with your project Git you have to do an initial synchronization step:
|
49
|
+
|
50
|
+
> rim sync -c -u <gerrit path> -r <branch or tag> -m <message header> -i <ignore patterns> <local directory>
|
51
|
+
|
52
|
+
which actually means the following:
|
53
|
+
|
54
|
+
1. The option -c indicates that we want to create a new rim module folder at the local specified with <local directory>. If <local directory> is already part of a module folder synchronized this will result in an error.
|
55
|
+
2. The mandatory option -u specifies the remote repository holding the module's content (the Module Git)
|
56
|
+
3. The mandatory option -r specifies the revision to synchronize with, typically a branch (such as master) or a specific tag.
|
57
|
+
4. The option -m helps you to define a header message text for the commits of rim. This option is important if your project requires a certain Git message header pattern.
|
58
|
+
5. The option -i can be used to specify patterns of files/folders which are specific only to this project and are not expected or allowed to be part of the Module Git. Files or folders matching to one of the patterns aren't removed when synchronizing content and wont't be forwarded to the Module Git when uploading.
|
59
|
+
|
60
|
+
### Example:
|
61
|
+
|
62
|
+
> rim sync -c -u libraries/modules/projectA -r master -m "PROJ-123/ThHe: integrated projectA module" -i CMakeLists.txt projectA
|
63
|
+
|
64
|
+
lets rim synchronize the state of branch master from the remote repository `ssh://gerrit/libraries/modules/projectA` into the relative folder projectA and won't touch files named CMakeLists.txt that are already within this folder. The corresponding commit message header will be "PROJ-123/ThHe: integrated projectA module"
|
65
|
+
|
66
|
+
## The magic rim integration branch
|
67
|
+
|
68
|
+
A call to rim sync actually does not change anything on the current branch in your Project Git. In fact all changes are committed to a special branch - the rim integration branch. It s managed automatically and named by adding the prefix 'rim/' to your current branch's name. So if your working branch is called 'master' all changes of rim sync will be commited to the branch 'rim/master'.
|
69
|
+
The rim integration branch will be automatically created if it is not existing or the latest remote revision is not (transitive) parent of the branch. In this case the branch will be created on the latest clean revision that only has clean parent revisions.
|
70
|
+
To get the changes commited to the rim integration branch into your working branch you simply rebase using git, e.g.:
|
71
|
+
|
72
|
+
> git rebase rim/master
|
73
|
+
|
74
|
+
*Never change (e.g. squash or amend) a commit created by rim after rebasing! This could cause conflicts on the .riminfo file on subsequent rebasing.*
|
75
|
+
|
76
|
+
## Synchronize again
|
77
|
+
|
78
|
+
The rim tool stores all the settings given by the initial rim sync call within a .riminfo file in the root of the module folder.
|
79
|
+
|
80
|
+
*This file shall not be changed manually and it will cause rim to ignore the content if it has been touched.*
|
81
|
+
|
82
|
+
Unless you intentionally want to change the synchronization settings for a specific module you never have to specify those settings in a subsequent call to rim sync again. So once you've integrated a module with rim you're able to resynchronize the contents of module folders using just:
|
83
|
+
|
84
|
+
> rim sync -m <message header> <local directory>
|
85
|
+
|
86
|
+
This will cause rim to read out the settings from the module's .riminfo file and do exactly the same as described for the initial synchronization step above. Note that it makes sense to think about the correct message header (although it's optional). If there were changes to the module's revision stored in the .riminfo file (e.g. the specified branch has moved in the module Git) then you will find the appropriate commit in the corresponding rim integration branch. Otherwise rim will indicate that there were no changes and you're done.
|
87
|
+
If you want to change the configuration of a module integrated with rim (e.g. you want to integrate a certain revision) you can simply call rim sync by specifying all options you want to change:
|
88
|
+
|
89
|
+
> rim sync -u <gerrit path> -r <branch or tag> -m <message header> -i <ignore patterns> <local directory>
|
90
|
+
|
91
|
+
This means:
|
92
|
+
|
93
|
+
1. If you want to change the remote repository specify the -u option as described above
|
94
|
+
2. Use the -r option if you need another branch or tag to synchronize with
|
95
|
+
3. If you want to change the list of files or folders to ignore then specify the new list using -i.
|
96
|
+
The -i option allows you only to replace the ignore list completely. So to append a new pattern to this list don't forget to also specify the previous entries.
|
97
|
+
|
98
|
+
### Example:
|
99
|
+
|
100
|
+
> rim sync -r release_1.1.2 projectA
|
101
|
+
|
102
|
+
lets rim commit the content of the tag or branch release_1.1.2 (same repository, same ignore patterns, automatically created commit message) to the integration branch.
|
103
|
+
|
104
|
+
## Modify and commit files in a Module Directory
|
105
|
+
|
106
|
+
If you're owner of a library module and thus are authorized to do changes in the module's sources rim supports you in doing that from within your Project Git: whenever you have the need of modifying files in a module directory you can do that in your project directory. Make your changes as needed and commit them to your local project repository.
|
107
|
+
|
108
|
+
*You cannot simply push the changes to the remote repository. The remote server will reject your direct push because module folders are touched and thus got "dirty". This behaviour ensures that no unintended modifications of library modules can creep into your project code.*
|
109
|
+
|
110
|
+
So if you're not allowed to commit changes to a library module: reset your branch to a clean rim status, otherwise you will never be able to push anything again.
|
111
|
+
|
112
|
+
### But how can a module owner get the local changes to the library module Git?
|
113
|
+
|
114
|
+
Supposed you are authorized and you now want to publish your module changes (i.e. push them to the remote project repository) the way is as follows:
|
115
|
+
|
116
|
+
1. Use rim to upload your changes to the review branch in Gerrit.
|
117
|
+
2. As soon as the review is successful and the modifications are applied to your module Git you use rim sync to resynchronize the changes into your local repository again – after the rebase and if you did no further changes your module is "clean" again.
|
118
|
+
3. Now that the module has reached a clean rim status you can commit your change to the remote project repository.
|
119
|
+
|
120
|
+
In the next sections we will have a more detailled look on integrating changes to library modules.
|
121
|
+
|
122
|
+
### Prepare your repository for work
|
123
|
+
|
124
|
+
Before using rim to upload changes from the Project Git to a Module Git you should prepare your local project repository:
|
125
|
+
|
126
|
+
* Use curl or scp to inject the Gerrit commit-msg hook (which adds automatically Gerrit-ChangeIds to your message) using one of the following lines:
|
127
|
+
|
128
|
+
~~~
|
129
|
+
> curl -Lo <local path to project git>/.git/hooks/commit-msg http://gerrit/tools/hooks/commit-msg
|
130
|
+
~~~
|
131
|
+
|
132
|
+
or
|
133
|
+
|
134
|
+
> scp -p gerrit:hooks/commit-msg <local path to project git>/.git/hooks/
|
135
|
+
|
136
|
+
* Make sure that the downloaded hook file is executable:
|
137
|
+
|
138
|
+
~~~
|
139
|
+
> chmod u+x <local path to project git>/.git/hooks/commit-msg
|
140
|
+
~~~
|
141
|
+
|
142
|
+
### Upload to the review branch
|
143
|
+
|
144
|
+
To track the quality of module changes all modifications to a library module have to be reviewed (using Gerrit). So similar to the workflow with repo all changes are first committed to the corresponding review branch. rim helps you in forwarding your module changes to Gerrit:
|
145
|
+
|
146
|
+
> rim upload <local directory>
|
147
|
+
|
148
|
+
With this command rim collects your changes to the specific module directory and commits a copy of the content to the corresponding branch that you specified for the module. So if you have specified master as the target revision of your module then your changes will be pushed to the refs/for/master branch (just like repo does).
|
149
|
+
|
150
|
+
*Only files are uploaded which do not match one the patterns specified in the rim ignore list (-i option of rim sync). So to avoid upload of project-only files specify them in the ignore list.*
|
151
|
+
|
152
|
+
*You can upload changes only if you specified a branch (-r option of rim sync) for your module, rim refuses uploads for tag or SHA1 revisions.*
|
153
|
+
|
154
|
+
### Resynchronize your reviewed changes from the Module Git
|
155
|
+
|
156
|
+
If you have a merciful reviewer or he just likes what you did then your changes will be submitted to the remote branch of the Module Git. If your intention was just to submit this change to your Module Git then your work is done. But normally you also want to get ahead in your project. Therefore you still want to push the commited and reviewed changes also to your remote project repository. This can now easily be done by using rim sync:
|
157
|
+
|
158
|
+
* Synchronize with curren revision.
|
159
|
+
|
160
|
+
~~~
|
161
|
+
> rim sync -m <message header> <local directory>
|
162
|
+
~~~
|
163
|
+
|
164
|
+
* Rebase on rim integration branch
|
165
|
+
|
166
|
+
~~~
|
167
|
+
> git rebase rim/<current branch>
|
168
|
+
~~~
|
169
|
+
|
170
|
+
as described earlier. Proposed you haven't changed anything in your module since your last rim upload this rebase should have simply replaced the module's .riminfo file and thus made this folder clean again.
|
171
|
+
|
172
|
+
### Correct rejected changes
|
173
|
+
|
174
|
+
In case your modifications are rejected by the reviewer you can simply adjust your code and upload your changes again by doing the following steps:
|
175
|
+
|
176
|
+
* Correct your code corresponding to the results of the review. But now commit the changes by amending your previous commit:
|
177
|
+
|
178
|
+
~~~
|
179
|
+
> git commit --amend
|
180
|
+
~~~
|
181
|
+
|
182
|
+
This will keep the correct ChangeId for the corresponding Gerrit in your commit and it will avoid a second "dirty" commit in your project repository.
|
183
|
+
|
184
|
+
* Upload the changes again with rim upload as described above and wait for the next Gerrit review result.
|
data/lib/rim/command/sync.rb
CHANGED
@@ -24,6 +24,12 @@ class Sync < Command
|
|
24
24
|
"Specify the remote URL and the target revision with the options.") do
|
25
25
|
@create = true
|
26
26
|
end
|
27
|
+
opts.on("-a", "--all", "Collects all modules from the specified paths.") do
|
28
|
+
@all = true
|
29
|
+
end
|
30
|
+
opts.on("-e", "--exclude=[PATTERN_LIST]", String, "Exclude all modules of a comma separated list of directories when using sync with -a option.") do |dirlist|
|
31
|
+
@excludedirs = dirlist.split(",")
|
32
|
+
end
|
27
33
|
@module_options = {}
|
28
34
|
opts.on("-u", "--remote-url URL", String, "Set the remote URL of the module.", \
|
29
35
|
"A relative path will be applied to ssh://gerrit/") do |url|
|
@@ -32,12 +38,18 @@ class Sync < Command
|
|
32
38
|
opts.on("-r", "--target-revision REVISION", String, "Set the target revision of the module.") do |target_revision|
|
33
39
|
@module_options[:target_revision] = target_revision
|
34
40
|
end
|
35
|
-
opts.on("-i", "--ignore
|
41
|
+
opts.on("-i", "--ignore=[PATTERN_LIST]", String, "Set the ignore patterns by specifying a comma separated list.") do |ignores|
|
36
42
|
@module_options[:ignores] = ignores || ""
|
37
43
|
end
|
38
44
|
opts.on("-m", "--message MESSAGE", String, "Message header to provide to each commit.") do |message|
|
39
45
|
@message = message
|
40
46
|
end
|
47
|
+
opts.on("-s", "--split", "Create a separate commit for each module.") do
|
48
|
+
@split = true
|
49
|
+
end
|
50
|
+
opts.on("-b", "--rebase", "Rebase after successful sync.") do
|
51
|
+
@rebase = true
|
52
|
+
end
|
41
53
|
end
|
42
54
|
|
43
55
|
def invoke()
|
@@ -55,10 +67,10 @@ class Sync < Command
|
|
55
67
|
@module_options[:ignores]))
|
56
68
|
end
|
57
69
|
else
|
58
|
-
helper.modules_from_paths(ARGV, @module_options)
|
70
|
+
helper.modules_from_paths(@all ? helper.module_paths(ARGV, @excludedirs) : ARGV, @module_options)
|
59
71
|
end
|
60
72
|
helper.check_arguments
|
61
|
-
helper.sync(@message)
|
73
|
+
helper.sync(@message, @rebase, @split)
|
62
74
|
end
|
63
75
|
|
64
76
|
end
|
data/lib/rim/command_helper.rb
CHANGED
@@ -4,6 +4,7 @@ require 'rim/module_info'
|
|
4
4
|
require 'rim/rim_info'
|
5
5
|
require 'rim/manifest/json_reader'
|
6
6
|
require 'rim/status_builder'
|
7
|
+
require 'pathname'
|
7
8
|
|
8
9
|
module RIM
|
9
10
|
|
@@ -32,7 +33,7 @@ class CommandHelper < Processor
|
|
32
33
|
end
|
33
34
|
|
34
35
|
def create_module_info(remote_url, local_path, target_revision, ignores)
|
35
|
-
ModuleInfo.new(remote_url, get_relative_path(local_path), target_revision, ignores, get_remote_branch_format(remote_url))
|
36
|
+
ModuleInfo.new(remote_url, get_relative_path(local_path), target_revision, ignores, remote_url ? get_remote_branch_format(remote_url) : nil)
|
36
37
|
end
|
37
38
|
|
38
39
|
def modules_from_manifest(path)
|
@@ -46,12 +47,12 @@ class CommandHelper < Processor
|
|
46
47
|
def modules_from_paths(paths, opts = {})
|
47
48
|
if paths.empty?
|
48
49
|
module_from_path(nil, opts)
|
49
|
-
elsif paths.length == 1 || opts.
|
50
|
+
elsif paths.length == 1 || !opts.has_key?(:remote_url)
|
50
51
|
while !paths.empty?
|
51
52
|
module_from_path(paths.shift, opts)
|
52
53
|
end
|
53
54
|
else
|
54
|
-
raise RimException.new("Multiple modules cannot be used with
|
55
|
+
raise RimException.new("Multiple modules cannot be used with URL option.")
|
55
56
|
end
|
56
57
|
end
|
57
58
|
|
@@ -59,26 +60,40 @@ class CommandHelper < Processor
|
|
59
60
|
module_path = find_file_dir_in_workspace(path || ".", RimInfo::InfoFileName)
|
60
61
|
if module_path
|
61
62
|
rim_info = RimInfo.from_dir(module_path)
|
62
|
-
|
63
|
+
module_info = create_module_info(opts.has_key?(:remote_url) ? opts[:remote_url] : rim_info.remote_url, \
|
63
64
|
module_path, opts.has_key?(:target_revision) ? opts[:target_revision] : rim_info.target_revision, \
|
64
|
-
opts.has_key?(:ignores) ? opts[:ignores] : rim_info.ignores)
|
65
|
-
|
65
|
+
opts.has_key?(:ignores) ? opts[:ignores] : rim_info.ignores)
|
66
|
+
if module_info.valid?
|
67
|
+
add_unique_module_info(module_info)
|
68
|
+
module_path
|
69
|
+
else
|
70
|
+
raise RimException.new("Invalid .riminfo file found in directory '#{module_path}'.")
|
71
|
+
end
|
66
72
|
else
|
67
73
|
raise RimException.new(path ? "No module info found in '#{path}'." : "No module info found.")
|
68
74
|
end
|
69
75
|
end
|
70
76
|
|
71
|
-
def
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
+
def module_paths(paths, exclude_paths = nil)
|
78
|
+
module_paths = []
|
79
|
+
(paths.empty? ? ['.'] : paths).each do |p|
|
80
|
+
module_paths.concat(all_module_paths_from_path(p))
|
81
|
+
end
|
82
|
+
paths.clear
|
83
|
+
if exclude_paths
|
84
|
+
exclude_paths.each do |e|
|
85
|
+
all_module_paths_from_path(e).each do |p|
|
86
|
+
module_paths.delete(p)
|
87
|
+
end
|
77
88
|
end
|
78
|
-
true
|
79
89
|
end
|
90
|
+
module_paths.sort
|
80
91
|
end
|
81
|
-
|
92
|
+
|
93
|
+
def all_module_paths_from_path(path)
|
94
|
+
Dir.glob(File.join(path, "**/.riminfo")).map { |f| Pathname.new(File.expand_path(File.dirname(f))).relative_path_from(Pathname.pwd).to_s }
|
95
|
+
end
|
96
|
+
|
82
97
|
def add_unique_module_info(module_info)
|
83
98
|
if !@paths.include?(module_info.local_path)
|
84
99
|
@paths.push(module_info.local_path)
|
data/lib/rim/dirty_check.rb
CHANGED
@@ -47,7 +47,7 @@ class DirtyCheck
|
|
47
47
|
def self.dirty?(dir)
|
48
48
|
mi = RimInfo.from_dir(dir)
|
49
49
|
# always fails if there is no checksum
|
50
|
-
!mi.checksum || mi.checksum != self.new.calc_checksum(mi, dir)
|
50
|
+
mi.dirty? || !mi.checksum || mi.checksum != self.new.calc_checksum(mi, dir)
|
51
51
|
end
|
52
52
|
|
53
53
|
# returns nil if checksum can't be calculated due to missing info
|
data/lib/rim/module_helper.rb
CHANGED
@@ -8,11 +8,13 @@ module RIM
|
|
8
8
|
|
9
9
|
class ModuleHelper < Processor
|
10
10
|
|
11
|
+
attr_reader :module_info
|
12
|
+
|
11
13
|
def initialize(workspace_root, module_info, logger)
|
12
14
|
super(workspace_root, logger)
|
13
15
|
@module_info = module_info
|
14
|
-
@remote_url = get_absolute_remote_url(@module_info.remote_url)
|
15
|
-
@remote_path = remote_path(@module_info.remote_url)
|
16
|
+
@remote_url = get_absolute_remote_url(@module_info.remote_url) if @module_info.remote_url
|
17
|
+
@remote_path = remote_path(@module_info.remote_url) if @module_info.remote_url
|
16
18
|
@logger = logger
|
17
19
|
end
|
18
20
|
|
data/lib/rim/module_info.rb
CHANGED
data/lib/rim/processor.rb
CHANGED
@@ -85,6 +85,18 @@ def clone_or_fetch_repository(remote_url, local_path, clone_log = nil)
|
|
85
85
|
local_path
|
86
86
|
end
|
87
87
|
|
88
|
+
def commit(session, message)
|
89
|
+
msg_file = Tempfile.new('message')
|
90
|
+
begin
|
91
|
+
msg_file << message
|
92
|
+
msg_file.close
|
93
|
+
session.execute("git add --all")
|
94
|
+
session.execute("git commit -F #{msg_file.path}")
|
95
|
+
ensure
|
96
|
+
msg_file.close(true)
|
97
|
+
end
|
98
|
+
end
|
99
|
+
|
88
100
|
def each_module_parallel(task_desc, modules)
|
89
101
|
if !modules.empty?
|
90
102
|
@logger.debug "starting \"#{task_desc}\" for #{modules.size} modules\r"
|
data/lib/rim/rim_info.rb
CHANGED
@@ -51,7 +51,11 @@ class RimInfo
|
|
51
51
|
mi.from_s(content)
|
52
52
|
mi
|
53
53
|
end
|
54
|
-
|
54
|
+
|
55
|
+
def dirty?
|
56
|
+
@dirty
|
57
|
+
end
|
58
|
+
|
55
59
|
def from_s(content)
|
56
60
|
attrs = {}
|
57
61
|
# normalize line endings
|
@@ -60,7 +64,7 @@ class RimInfo
|
|
60
64
|
checksum = content[0..39]
|
61
65
|
# exclude \n after checksum
|
62
66
|
content = content[41..-1]
|
63
|
-
if content
|
67
|
+
if content
|
64
68
|
content.split("\n").each do |l|
|
65
69
|
col = l.index(":")
|
66
70
|
if col
|
@@ -70,13 +74,11 @@ class RimInfo
|
|
70
74
|
end
|
71
75
|
end
|
72
76
|
end
|
73
|
-
else
|
74
|
-
# checksum error, ignore content
|
75
|
-
# TODO: output user warning
|
76
77
|
end
|
77
78
|
AttrsDef.each do |a|
|
78
79
|
send("#{a}=".to_sym, attrs[a])
|
79
80
|
end
|
81
|
+
@dirty = checksum != calc_sha1(content)
|
80
82
|
end
|
81
83
|
|
82
84
|
def from_dir(dir)
|
data/lib/rim/sync_helper.rb
CHANGED
@@ -19,12 +19,13 @@ class SyncHelper < CommandHelper
|
|
19
19
|
end
|
20
20
|
|
21
21
|
# sync all module changes into rim branch
|
22
|
-
def sync(message = nil)
|
22
|
+
def sync(message = nil, rebase = nil, split = true)
|
23
23
|
# get the name of the current workspace branch
|
24
24
|
RIM::git_session(@ws_root) do |s|
|
25
25
|
branch = s.current_branch
|
26
26
|
rim_branch = "rim/" + branch
|
27
27
|
branch_sha1 = nil
|
28
|
+
changed_modules = nil
|
28
29
|
if branch.empty?
|
29
30
|
raise RimException.new("Not on a git branch.")
|
30
31
|
elsif branch.start_with?("rim/")
|
@@ -35,6 +36,7 @@ class SyncHelper < CommandHelper
|
|
35
36
|
rev = get_latest_clean_path_revision(s, branch, remote_rev)
|
36
37
|
if !s.has_branch?(rim_branch) || has_ancestor?(s, branch, s.rev_sha1(rim_branch)) || !has_ancestor?(s, rim_branch, remote_rev)
|
37
38
|
s.execute("git branch -f #{rim_branch} #{rev}")
|
39
|
+
branch_sha1 = s.rev_sha1(rim_branch)
|
38
40
|
end
|
39
41
|
remote_url = "file://" + @ws_root
|
40
42
|
tmpdir = clone_or_fetch_repository(remote_url, module_tmp_git_path(".ws"), "Cloning workspace git...")
|
@@ -47,13 +49,21 @@ class SyncHelper < CommandHelper
|
|
47
49
|
tmp_session.execute("git clean -xdf")
|
48
50
|
tmp_session.execute("git checkout #{rim_branch}")
|
49
51
|
end
|
50
|
-
|
51
|
-
|
52
|
+
changed_modules = sync_modules(tmp_session, message)
|
53
|
+
if !split
|
54
|
+
tmp_session.execute("git reset --soft #{branch_sha1}")
|
55
|
+
commit(tmp_session, message ? message : get_commit_message(changed_modules)) if tmp_session.uncommited_changes?
|
56
|
+
end
|
52
57
|
tmp_session.execute("git push #{remote_url} #{rim_branch}:#{rim_branch}")
|
53
58
|
end
|
54
59
|
end
|
55
|
-
if
|
56
|
-
|
60
|
+
if !changed_modules.empty?
|
61
|
+
if rebase
|
62
|
+
s.execute("git rebase #{rim_branch}")
|
63
|
+
@logger.info("Changes have been commited to branch #{rim_branch} and workspace has been rebased successfully.")
|
64
|
+
else
|
65
|
+
@logger.info("Changes have been commited to branch #{rim_branch}. Rebase to apply changes to workspace.")
|
66
|
+
end
|
57
67
|
else
|
58
68
|
@logger.info("No changes.")
|
59
69
|
end
|
@@ -67,9 +77,14 @@ private
|
|
67
77
|
@module_infos.each do |module_info|
|
68
78
|
module_helpers.push(SyncModuleHelper.new(session.execute_dir, @ws_root, module_info, @logger))
|
69
79
|
end
|
80
|
+
changed_modules = []
|
70
81
|
module_helpers.each do |m|
|
71
|
-
m.
|
82
|
+
@logger.info("Synchronizing #{m.module_info.local_path}...")
|
83
|
+
if m.sync(message)
|
84
|
+
changed_modules << m.module_info
|
85
|
+
end
|
72
86
|
end
|
87
|
+
changed_modules
|
73
88
|
end
|
74
89
|
|
75
90
|
# get latest revision from which all parent revisions are clean
|
@@ -116,6 +131,18 @@ private
|
|
116
131
|
!parents.empty? ? parents.first : nil
|
117
132
|
end
|
118
133
|
|
134
|
+
#create default commit message from array of changed modules
|
135
|
+
def get_commit_message(changed_modules)
|
136
|
+
StringIO.open do |s|
|
137
|
+
s.puts "rim sync."
|
138
|
+
s.puts
|
139
|
+
changed_modules.each do |m|
|
140
|
+
s.puts m.local_path
|
141
|
+
end
|
142
|
+
s.string
|
143
|
+
end
|
144
|
+
end
|
145
|
+
|
119
146
|
end
|
120
147
|
|
121
148
|
end
|
@@ -22,6 +22,7 @@ module RIM
|
|
22
22
|
# export +revision+ of +mod+ into working copy
|
23
23
|
# BEWARE: any changes to the working copy target dir will be lost!
|
24
24
|
def export_module(message)
|
25
|
+
changes = false
|
25
26
|
RIM::git_session(@dest_root) do |d|
|
26
27
|
start_sha1 = d.rev_sha1("HEAD")
|
27
28
|
git_path = module_git_path(@remote_path)
|
@@ -44,26 +45,10 @@ module RIM
|
|
44
45
|
end
|
45
46
|
temp_commit(d, "commit changes") if needs_commit?(d)
|
46
47
|
d.execute("git reset --soft #{start_sha1}")
|
47
|
-
|
48
|
-
|
49
|
-
end
|
50
|
-
|
51
|
-
def commit(message)
|
52
|
-
RIM::git_session(@dest_root) do |s|
|
53
|
-
msg_file = Tempfile.new('message')
|
54
|
-
begin
|
55
|
-
if message
|
56
|
-
msg_file << message
|
57
|
-
else
|
58
|
-
msg_file << "rim sync: module #{@module_info.local_path}"
|
59
|
-
end
|
60
|
-
msg_file.close
|
61
|
-
s.execute("git add --all")
|
62
|
-
s.execute("git commit -F #{msg_file.path}")
|
63
|
-
ensure
|
64
|
-
msg_file.close(true)
|
65
|
-
end
|
48
|
+
changes = d.uncommited_changes?
|
49
|
+
commit(d, message || "rim sync: module #{@module_info.local_path}") if changes
|
66
50
|
end
|
51
|
+
changes
|
67
52
|
end
|
68
53
|
|
69
54
|
def needs_commit?(session)
|
data/lib/rim/version.rb
CHANGED
data/test/rim_info_test.rb
CHANGED
@@ -32,6 +32,7 @@ def test_read
|
|
32
32
|
d = empty_test_dir("rim_info")
|
33
33
|
create_rim_info(d, :remote_url => "ssh://gerrit")
|
34
34
|
ri = RIM::RimInfo.from_dir(d)
|
35
|
+
assert !ri.dirty?
|
35
36
|
assert_equal "ssh://gerrit", ri.remote_url
|
36
37
|
end
|
37
38
|
|
@@ -47,7 +48,7 @@ def test_tamper
|
|
47
48
|
end
|
48
49
|
# after
|
49
50
|
ri = RIM::RimInfo.from_dir(d)
|
50
|
-
|
51
|
+
assert ri.dirty?
|
51
52
|
end
|
52
53
|
|
53
54
|
def test_line_ending_change
|
@@ -65,6 +66,7 @@ def test_line_ending_change
|
|
65
66
|
end
|
66
67
|
# still valid
|
67
68
|
ri = RIM::RimInfo.from_dir(d)
|
69
|
+
assert !ri.dirty?
|
68
70
|
assert_equal "ssh://gerrit", ri.remote_url
|
69
71
|
end
|
70
72
|
|
metadata
CHANGED
@@ -1,27 +1,30 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: esr-rim
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.
|
4
|
+
version: 1.2.0
|
5
|
+
prerelease:
|
5
6
|
platform: ruby
|
6
7
|
authors:
|
7
8
|
- ESR Labs AG
|
8
9
|
autorequire:
|
9
10
|
bindir: bin
|
10
11
|
cert_chain: []
|
11
|
-
date: 2015-
|
12
|
+
date: 2015-09-18 00:00:00.000000000 Z
|
12
13
|
dependencies:
|
13
14
|
- !ruby/object:Gem::Dependency
|
14
15
|
name: subcommand
|
15
16
|
requirement: !ruby/object:Gem::Requirement
|
17
|
+
none: false
|
16
18
|
requirements:
|
17
|
-
- - '>='
|
19
|
+
- - ! '>='
|
18
20
|
- !ruby/object:Gem::Version
|
19
21
|
version: 1.0.6
|
20
22
|
type: :runtime
|
21
23
|
prerelease: false
|
22
24
|
version_requirements: !ruby/object:Gem::Requirement
|
25
|
+
none: false
|
23
26
|
requirements:
|
24
|
-
- - '>='
|
27
|
+
- - ! '>='
|
25
28
|
- !ruby/object:Gem::Version
|
26
29
|
version: 1.0.6
|
27
30
|
description: RIM lets you work with multiple git repositories from within one single
|
@@ -82,7 +85,6 @@ files:
|
|
82
85
|
- bin/rim
|
83
86
|
homepage: http://esrlabs.com
|
84
87
|
licenses: []
|
85
|
-
metadata: {}
|
86
88
|
post_install_message:
|
87
89
|
rdoc_options:
|
88
90
|
- --main
|
@@ -92,19 +94,21 @@ rdoc_options:
|
|
92
94
|
require_paths:
|
93
95
|
- lib
|
94
96
|
required_ruby_version: !ruby/object:Gem::Requirement
|
97
|
+
none: false
|
95
98
|
requirements:
|
96
|
-
- - '>='
|
99
|
+
- - ! '>='
|
97
100
|
- !ruby/object:Gem::Version
|
98
101
|
version: '0'
|
99
102
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
103
|
+
none: false
|
100
104
|
requirements:
|
101
|
-
- - '>='
|
105
|
+
- - ! '>='
|
102
106
|
- !ruby/object:Gem::Version
|
103
107
|
version: '0'
|
104
108
|
requirements: []
|
105
109
|
rubyforge_project:
|
106
|
-
rubygems_version:
|
110
|
+
rubygems_version: 1.8.23
|
107
111
|
signing_key:
|
108
|
-
specification_version:
|
112
|
+
specification_version: 3
|
109
113
|
summary: RIM - multi git tool
|
110
114
|
test_files: []
|
checksums.yaml
DELETED
@@ -1,7 +0,0 @@
|
|
1
|
-
---
|
2
|
-
SHA1:
|
3
|
-
metadata.gz: e39178ba7e2f000cec05a0ca417d4064b1c06cb6
|
4
|
-
data.tar.gz: e51d10cecfd216dcb0890a5b3a47ab13086c46c4
|
5
|
-
SHA512:
|
6
|
-
metadata.gz: a09bfcc5ef6fd0138f5c3be1be93c9c19da499cfd6701cf5efc46eafb3c213b047a8aa0e6eb0b6342f42884a65f1913a5776631104f50970bcc30c64167ed9cb
|
7
|
-
data.tar.gz: 7941fdf8455ba6ccc8594a89fe17634ad82f3458aee8a56e6871c65834ddbdd17808c18ff58b1d1b2adc60f81d3c71fbd9ad5e8b05510f91039290fe202626eb
|