PageRenderTime 36ms CodeModel.GetById 17ms app.highlight 13ms RepoModel.GetById 1ms app.codeStats 0ms

/Mercurial.Net/CloneCommand.cs

#
C# | 431 lines | 188 code | 34 blank | 209 comment | 3 complexity | 1f4825631084a1c01068d30788a38ba1 MD5 | raw file
  1using System;
  2using System.Collections.Generic;
  3using System.Collections.ObjectModel;
  4using System.ComponentModel;
  5using System.Linq;
  6using Mercurial.Attributes;
  7
  8namespace Mercurial
  9{
 10    /// <summary>
 11    /// This class implements the "hg clone" command (<see href="http://www.selenic.com/mercurial/hg.1.html#clone"/>):
 12    /// make a copy of an existing repository.
 13    /// </summary>
 14    public sealed class CloneCommand : MercurialCommandBase<CloneCommand>
 15    {
 16        /// <summary>
 17        /// This is the backing field for the <see cref="Branches"/> property.
 18        /// </summary>
 19        private readonly List<string> _Branches = new List<string>();
 20
 21        /// <summary>
 22        /// This is the backing field for the <see cref="Revisions"/> property.
 23        /// </summary>
 24        private readonly List<RevSpec> _Revisions = new List<RevSpec>();
 25
 26        /// <summary>
 27        /// This is the backing field for the <see cref="Source"/> property.
 28        /// </summary>
 29        private string _Source = string.Empty;
 30
 31        /// <summary>
 32        /// This is the backing field for the <see cref="SshCommand"/> property.
 33        /// </summary>
 34        private string _SshCommand = string.Empty;
 35
 36        /// <summary>
 37        /// This is the backing field for the <see cref="RemoteCommand"/> property.
 38        /// </summary>
 39        private string _RemoteCommand = string.Empty;
 40
 41        /// <summary>
 42        /// This is the backing field for the <see cref="VerifyServerCertificate"/> property.
 43        /// </summary>
 44        private bool _VerifyServerCertificate = true;
 45
 46        /// <summary>
 47        /// Initializes a new instance of the <see cref="CloneCommand"/> class.
 48        /// </summary>
 49        public CloneCommand()
 50            : base("clone")
 51        {
 52            Update = true;
 53            CompressedTransfer = true;
 54        }
 55
 56        /// <summary>
 57        /// Gets or sets the source path or Uri to clone from.
 58        /// </summary>
 59        [DefaultValue("")]
 60        public string Source
 61        {
 62            get
 63            {
 64                return _Source;
 65            }
 66
 67            set
 68            {
 69                _Source = (value ?? string.Empty).Trim();
 70            }
 71        }
 72
 73        /// <summary>
 74        /// Gets or sets a value indicating whether to update the clone with a working folder.
 75        /// Default is <c>true</c>.
 76        /// </summary>
 77        [BooleanArgument(FalseOption = "--noupdate")]
 78        [DefaultValue(true)]
 79        public bool Update
 80        {
 81            get;
 82            set;
 83        }
 84
 85        /// <summary>
 86        /// Gets or sets a value indicating whether to verify the server certificate. If set to <c>false</c>, will ignore web.cacerts configuration.
 87        /// Default value is <c>true</c>.
 88        /// </summary>
 89        [BooleanArgument(FalseOption = "--insecure")]
 90        [DefaultValue(true)]
 91        public bool VerifyServerCertificate
 92        {
 93            get
 94            {
 95                return _VerifyServerCertificate;
 96            }
 97
 98            set
 99            {
100                RequiresVersion(new Version(1, 7, 5), "VerifyServerCertificate property of the CloneCommand class");
101                _VerifyServerCertificate = value;
102            }
103        }
104
105        /// <summary>
106        /// Sets the <see cref="VerifyServerCertificate"/> property to the specified value and
107        /// returns this <see cref="CloneCommand"/> instance.
108        /// </summary>
109        /// <param name="value">
110        /// The new value for the <see cref="VerifyServerCertificate"/> property.
111        /// </param>
112        /// <returns>
113        /// This <see cref="CloneCommand"/> instance.
114        /// </returns>
115        /// <remarks>
116        /// This method is part of the fluent interface.
117        /// </remarks>
118        public CloneCommand WithVerifyServerCertificate(bool value)
119        {
120            VerifyServerCertificate = value;
121            return this;
122        }
123
124        /// <summary>
125        /// Gets or sets the <see cref="Revisions"/> to update the working
126        /// folder to, or <c>null</c> to update to the tip. Default is <c>null</c>.
127        /// </summary>
128        [NullableArgument(NonNullOption = "--updaterev")]
129        [DefaultValue(null)]
130        public RevSpec UpdateToRevision
131        {
132            get;
133            set;
134        }
135
136        /// <summary>
137        /// Gets or sets a value indicating whether to use compressed transfer or not. Over LAN, uncompressed is faster, otherwise
138        /// compressed is most likely faster. Default is <c>true</c>.
139        /// </summary>
140        [BooleanArgument(FalseOption = "--uncompressed")]
141        [DefaultValue(true)]
142        public bool CompressedTransfer
143        {
144            get;
145            set;
146        }
147
148        /// <summary>
149        /// Gets the collection of revisions to include in the clone. If empty, include every changeset
150        /// from the source repository. Default is empty.
151        /// </summary>
152        [RepeatableArgument(Option = "--rev")]
153        public Collection<RevSpec> Revisions
154        {
155            get
156            {
157                return new Collection<RevSpec>(_Revisions);
158            }
159        }
160
161        /// <summary>
162        /// Gets the collection of branches to include in the clone. If empty, include every branch
163        /// from the source repository. Default is empty.
164        /// </summary>
165        [RepeatableArgument(Option = "--branch")]
166        public Collection<string> Branches
167        {
168            get
169            {
170                return new Collection<string>(_Branches);
171            }
172        }
173
174        /// <summary>
175        /// Gets or sets a value indicating whether to use pull protocol to copy metadata.
176        /// Default value is <c>false</c>.
177        /// </summary>
178        [DefaultValue(false)]
179        public bool UsePull
180        {
181            get;
182            set;
183        }
184
185        /// <summary>
186        /// Sets the <see cref="UsePull"/> property to the specified value and
187        /// returns this <see cref="CloneCommand"/> instance.
188        /// </summary>
189        /// <param name="value">
190        /// The new value for the <see cref="UsePull"/> property.
191        /// </param>
192        /// <returns>
193        /// This <see cref="CloneCommand"/> instance.
194        /// </returns>
195        /// <remarks>
196        /// This method is part of the fluent interface.
197        /// </remarks>
198        public CloneCommand WithUsePull(bool value)
199        {
200            UsePull = value;
201            return this;
202        }
203
204        /// <summary>
205        /// Gets or sets the ssh command to use when cloning.
206        /// Default is <see cref="string.Empty"/>.
207        /// </summary>
208        [NullableArgument(NonNullOption = "--ssh")]
209        [DefaultValue("")]
210        public string SshCommand
211        {
212            get
213            {
214                return _SshCommand;
215            }
216
217            set
218            {
219                _SshCommand = (value ?? string.Empty).Trim();
220            }
221        }
222
223        /// <summary>
224        /// Gets or sets the hg command to run on the remote side.
225        /// Default is <see cref="string.Empty"/>.
226        /// </summary>
227        [NullableArgument(NonNullOption = "--remotecmd")]
228        [DefaultValue("")]
229        public string RemoteCommand
230        {
231            get
232            {
233                return _RemoteCommand;
234            }
235
236            set
237            {
238                _RemoteCommand = (value ?? string.Empty).Trim();
239            }
240        }
241
242        /// <summary>
243        /// Gets all the arguments to the <see cref="CommandBase{T}.Command"/>, or an
244        /// empty array if there are none.
245        /// </summary>
246        /// <value></value>
247        public override IEnumerable<string> Arguments
248        {
249            get
250            {
251                return base.Arguments.Concat(
252                    new[]
253                    {
254                        "\"" + Source + "\"", ".",
255                    });
256            }
257        }
258
259        /// <summary>
260        /// Sets the <see cref="Source"/> property to the specified value and
261        /// returns this <see cref="CloneCommand"/> instance.
262        /// </summary>
263        /// <param name="value">
264        /// The new value for the <see cref="Source"/> property.
265        /// </param>
266        /// <returns>
267        /// This <see cref="CloneCommand"/> instance.
268        /// </returns>
269        /// <remarks>
270        /// This method is part of the fluent interface.
271        /// </remarks>
272        public CloneCommand WithSource(string value)
273        {
274            Source = value;
275            return this;
276        }
277
278        /// <summary>
279        /// Sets the <see cref="SshCommand"/> property to the specified value and
280        /// returns this <see cref="CloneCommand"/> instance.
281        /// </summary>
282        /// <param name="value">
283        /// The new value for the <see cref="SshCommand"/> property.
284        /// </param>
285        /// <returns>
286        /// This <see cref="CloneCommand"/> instance.
287        /// </returns>
288        /// <remarks>
289        /// This method is part of the fluent interface.
290        /// </remarks>
291        public CloneCommand WithSshCommand(string value)
292        {
293            SshCommand = value;
294            return this;
295        }
296
297        /// <summary>
298        /// Sets the <see cref="RemoteCommand"/> property to the specified value and
299        /// returns this <see cref="CloneCommand"/> instance.
300        /// </summary>
301        /// <param name="value">
302        /// The new value for the <see cref="RemoteCommand"/> property.
303        /// </param>
304        /// <returns>
305        /// This <see cref="CloneCommand"/> instance.
306        /// </returns>
307        /// <remarks>
308        /// This method is part of the fluent interface.
309        /// </remarks>
310        public CloneCommand WithRemoteCommand(string value)
311        {
312            RemoteCommand = value;
313            return this;
314        }
315
316        /// <summary>
317        /// Sets the <see cref="Update"/> property to the specified value and
318        /// returns this <see cref="CloneCommand"/> instance.
319        /// </summary>
320        /// <param name="value">
321        /// The new value for the <see cref="Update"/> property.
322        /// </param>
323        /// <returns>
324        /// This <see cref="CloneCommand"/> instance.
325        /// </returns>
326        /// <remarks>
327        /// This method is part of the fluent interface.
328        /// </remarks>
329        public CloneCommand WithUpdate(bool value)
330        {
331            Update = value;
332            return this;
333        }
334
335        /// <summary>
336        /// Sets the <see cref="UpdateToRevision"/> property to the specified value and
337        /// returns this <see cref="CloneCommand"/> instance.
338        /// </summary>
339        /// <param name="value">
340        /// The new value for the <see cref="UpdateToRevision"/> property.
341        /// </param>
342        /// <returns>
343        /// This <see cref="CloneCommand"/> instance.
344        /// </returns>
345        /// <remarks>
346        /// This method is part of the fluent interface.
347        /// </remarks>
348        public CloneCommand WithUpdateToRevision(RevSpec value)
349        {
350            UpdateToRevision = value;
351            return this;
352        }
353
354        /// <summary>
355        /// Sets the <see cref="CompressedTransfer"/> property to the specified value and
356        /// returns this <see cref="CloneCommand"/> instance.
357        /// </summary>
358        /// <param name="value">
359        /// The new value for the <see cref="CompressedTransfer"/> property.
360        /// </param>
361        /// <returns>
362        /// This <see cref="CloneCommand"/> instance.
363        /// </returns>
364        /// <remarks>
365        /// This method is part of the fluent interface.
366        /// </remarks>
367        public CloneCommand WithCompressedTransfer(bool value)
368        {
369            CompressedTransfer = value;
370            return this;
371        }
372
373        /// <summary>
374        /// Adds the value to the <see cref="Revisions"/> collection property and
375        /// returns this <see cref="CloneCommand"/> instance.
376        /// </summary>
377        /// <param name="value">
378        /// The value to add to the <see cref="Revisions"/> collection property.
379        /// </param>
380        /// <returns>
381        /// This <see cref="CloneCommand"/> instance.
382        /// </returns>
383        /// <remarks>
384        /// This method is part of the fluent interface.
385        /// </remarks>
386        public CloneCommand WithRevision(RevSpec value)
387        {
388            Revisions.Add(value);
389            return this;
390        }
391
392        /// <summary>
393        /// Adds the value to the <see cref="Branches"/> collection property and
394        /// returns this <see cref="CloneCommand"/> instance.
395        /// </summary>
396        /// <param name="value">
397        /// The value to add to the <see cref="Branches"/> collection property.
398        /// </param>
399        /// <returns>
400        /// This <see cref="CloneCommand"/> instance.
401        /// </returns>
402        /// <remarks>
403        /// This method is part of the fluent interface.
404        /// </remarks>
405        public CloneCommand WithBranch(string value)
406        {
407            Branches.Add(value);
408            return this;
409        }
410
411        /// <summary>
412        /// Validates the command configuration. This method should throw the necessary
413        /// exceptions to signal missing or incorrect configuration (like attempting to
414        /// add files to the repository without specifying which files to add.)
415        /// </summary>
416        /// <exception cref="InvalidOperationException">
417        /// <para>The 'clone' command requires <see cref="Source"/> to be specified.</para>
418        /// <para>- or -</para>
419        /// <para>The <see cref="VerifyServerCertificate"/> command was used with Mercurial 1.7.4 or older.</para>
420        /// </exception>
421        public override void Validate()
422        {
423            base.Validate();
424
425            if (!VerifyServerCertificate && ClientExecutable.CurrentVersion < new Version(1, 7, 5))
426                throw new InvalidOperationException("The 'VerifyServerCertificate' property is only available in Mercurial 1.7.5 and newer");
427            if (StringEx.IsNullOrWhiteSpace(Source))
428                throw new InvalidOperationException("The 'clone' command requires Source to be specified");
429        }
430    }
431}