1 /* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
3 * Copyright (C) 2007 Imendio AB
5 * This program is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU General Public License as
7 * published by the Free Software Foundation; either version 2 of the
8 * License, or (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * General Public License for more details.
15 * You should have received a copy of the GNU General Public
16 * License along with this program; if not, write to the
17 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18 * Boston, MA 02111-1307, USA.
23 #include "giggle-git-diff.h"
25 typedef struct GiggleGitDiffPriv GiggleGitDiffPriv
;
27 struct GiggleGitDiffPriv
{
32 GiggleRevision
*patch_format
;
37 static void git_diff_finalize (GObject
*object
);
38 static void git_diff_get_property (GObject
*object
,
42 static void git_diff_set_property (GObject
*object
,
47 static gboolean
git_diff_get_command_line (GiggleJob
*job
,
48 gchar
**command_line
);
49 static void git_diff_handle_output (GiggleJob
*job
,
50 const gchar
*output_str
,
53 G_DEFINE_TYPE (GiggleGitDiff
, giggle_git_diff
, GIGGLE_TYPE_JOB
)
55 #define GET_PRIV(obj) (G_TYPE_INSTANCE_GET_PRIVATE ((obj), GIGGLE_TYPE_GIT_DIFF, GiggleGitDiffPriv))
66 giggle_git_diff_class_init (GiggleGitDiffClass
*class)
68 GObjectClass
*object_class
= G_OBJECT_CLASS (class);
69 GiggleJobClass
*job_class
= GIGGLE_JOB_CLASS (class);
71 object_class
->finalize
= git_diff_finalize
;
72 object_class
->get_property
= git_diff_get_property
;
73 object_class
->set_property
= git_diff_set_property
;
75 job_class
->get_command_line
= git_diff_get_command_line
;
76 job_class
->handle_output
= git_diff_handle_output
;
78 g_object_class_install_property (object_class
,
80 g_param_spec_object ("revision1",
82 "Revision 1 to make diff on",
85 g_object_class_install_property (object_class
,
87 g_param_spec_object ("revision2",
89 "Revision 2 to make diff on",
92 g_object_class_install_property (object_class
,
94 g_param_spec_pointer ("files",
96 "Files list to make diff on",
98 g_object_class_install_property (object_class
,
100 g_param_spec_object ("patch-format",
102 "The revision to output a patch format for",
103 GIGGLE_TYPE_REVISION
,
106 g_type_class_add_private (object_class
, sizeof (GiggleGitDiffPriv
));
110 giggle_git_diff_init (GiggleGitDiff
*dummy
)
115 git_diff_finalize (GObject
*object
)
117 GiggleGitDiffPriv
*priv
;
119 priv
= GET_PRIV (object
);
122 g_object_unref (priv
->rev1
);
126 g_object_unref (priv
->rev2
);
129 g_free (priv
->result
);
131 g_list_foreach (priv
->files
, (GFunc
) g_free
, NULL
);
132 g_list_free (priv
->files
);
134 if (priv
->patch_format
) {
135 g_object_unref (priv
->patch_format
);
138 G_OBJECT_CLASS (giggle_git_diff_parent_class
)->finalize (object
);
142 git_diff_get_property (GObject
*object
,
147 GiggleGitDiffPriv
*priv
;
149 priv
= GET_PRIV (object
);
153 g_value_set_object (value
, priv
->rev1
);
156 g_value_set_object (value
, priv
->rev2
);
159 g_value_set_pointer (value
, priv
->files
);
161 case PROP_PATCH_FORMAT
:
162 g_value_set_object (value
, priv
->patch_format
);
165 G_OBJECT_WARN_INVALID_PROPERTY_ID (object
, param_id
, pspec
);
171 git_diff_set_property (GObject
*object
,
176 GiggleGitDiffPriv
*priv
;
178 priv
= GET_PRIV (object
);
183 g_object_unref (priv
->rev1
);
185 #if GLIB_MAJOR_VERSION > 2 || GLIB_MINOR_VERSION > 12
186 priv
->rev1
= g_value_dup_object (value
);
188 priv
->rev1
= GIGGLE_REVISION (g_value_dup_object (value
));
193 g_object_unref (priv
->rev2
);
195 #if GLIB_MAJOR_VERSION > 2 || GLIB_MINOR_VERSION > 12
196 priv
->rev2
= g_value_dup_object (value
);
198 priv
->rev2
= GIGGLE_REVISION (g_value_dup_object (value
));
202 priv
->files
= g_value_get_pointer (value
);
204 case PROP_PATCH_FORMAT
:
205 priv
->patch_format
= g_value_get_object (value
);
208 G_OBJECT_WARN_INVALID_PROPERTY_ID (object
, param_id
, pspec
);
214 git_diff_get_command_line (GiggleJob
*job
, gchar
**command_line
)
216 GiggleGitDiffPriv
*priv
;
220 priv
= GET_PRIV (job
);
224 * Git currently (20071009) v1.5.2.1 only supports:
228 * for COMPLETE changes sets to a branch, you can't use this
229 * command for a selection of files you have changed, also, it
230 * only works for committed work, not uncommitted work AFAICS.
232 if (priv
->patch_format
) {
233 str
= g_string_new (GIT_COMMAND
" format-patch");
235 g_string_append_printf (str
, " %s -1",
236 giggle_revision_get_sha (priv
->patch_format
));
238 str
= g_string_new (GIT_COMMAND
" diff");
241 g_string_append_printf (str
, " %s", giggle_revision_get_sha (priv
->rev1
));
245 g_string_append_printf (str
, " %s", giggle_revision_get_sha (priv
->rev2
));
249 g_string_append_printf (str
, " %s", (gchar
*) files
->data
);
254 *command_line
= g_string_free (str
, FALSE
);
259 git_diff_handle_output (GiggleJob
*job
,
260 const gchar
*output_str
,
263 GiggleGitDiffPriv
*priv
;
265 priv
= GET_PRIV (job
);
267 priv
->result
= g_strdup (output_str
);
271 giggle_git_diff_new (void)
273 return g_object_new (GIGGLE_TYPE_GIT_DIFF
, NULL
);
277 giggle_git_diff_set_revisions (GiggleGitDiff
*diff
,
278 GiggleRevision
*rev1
,
279 GiggleRevision
*rev2
)
281 g_return_if_fail (GIGGLE_IS_GIT_DIFF (diff
));
282 g_return_if_fail (!rev1
|| GIGGLE_IS_REVISION (rev1
));
283 g_return_if_fail (!rev2
|| GIGGLE_IS_REVISION (rev2
));
292 giggle_git_diff_set_files (GiggleGitDiff
*diff
,
295 GiggleGitDiffPriv
*priv
;
297 g_return_if_fail (GIGGLE_IS_GIT_DIFF (diff
));
299 priv
= GET_PRIV (diff
);
302 g_warning ("You have the 'patch-format' property set to TRUE. "
303 "Use of the git-format-patch command does not allow specific files. "
304 "These files will be ignored while 'patch-format' is TRUE.");
313 giggle_git_diff_set_patch_format (GiggleGitDiff
*diff
,
316 GiggleGitDiffPriv
*priv
;
318 g_return_if_fail (GIGGLE_IS_GIT_DIFF (diff
));
319 g_return_if_fail (GIGGLE_IS_REVISION (rev
));
321 priv
= GET_PRIV (diff
);
324 g_warning ("Use of the git-format-patch command does not allow specific files. "
325 "You have files set for this GiggleGitDiff which will be ignored.");
334 giggle_git_diff_get_patch_format (GiggleGitDiff
*diff
)
336 GiggleGitDiffPriv
*priv
;
338 g_return_val_if_fail (GIGGLE_IS_GIT_DIFF (diff
), NULL
);
340 priv
= GET_PRIV (diff
);
342 return priv
->patch_format
;
346 giggle_git_diff_get_result (GiggleGitDiff
*diff
)
348 GiggleGitDiffPriv
*priv
;
350 g_return_val_if_fail (GIGGLE_IS_GIT_DIFF (diff
), NULL
);
352 priv
= GET_PRIV (diff
);