コード例 #1
0
ファイル: WebGreaseContext.cs プロジェクト: ymf1/webgrease
        /// <summary>The parallel for each call, that ensures valid multi threaded opeartions for webgrease calls.</summary>
        /// <param name="idParts">The id parts.</param>
        /// <param name="items">The items.</param>
        /// <param name="parallelAction">The parallel action.</param>
        /// <param name="serialAction">The serial action.</param>
        /// <typeparam name="T">The type of items</typeparam>
        public void ParallelForEach <T>(Func <T, string[]> idParts, IEnumerable <T> items, Func <IWebGreaseContext, T, ParallelLoopState, bool> parallelAction, Func <IWebGreaseContext, T, bool> serialAction = null)
        {
            var id = idParts(default(T));

            this.SectionedAction(id).Execute(() =>
            {
                var serialLock           = new object();
                var parallelForEachItems = new List <Tuple <IWebGreaseContext, DelayedLogManager, T> >();
                var done = 0;
                foreach (var item in items)
                {
                    // TODO: Better name then item ToString?
                    var delayedLogManager = new DelayedLogManager(this.Log, item.ToString());
                    var threadContext     = new WebGreaseContext(new WebGreaseConfiguration(this.Configuration), delayedLogManager.LogManager, this.Cache.CurrentCacheSection, this.Preprocessing);

                    var success = true;
                    if (serialAction != null)
                    {
                        success = serialAction(threadContext, item);
                    }

                    if (success)
                    {
                        parallelForEachItems.Add(new Tuple <IWebGreaseContext, DelayedLogManager, T>(threadContext, delayedLogManager, item));
                    }
                }

                Parallel.ForEach(
                    parallelForEachItems,
                    (item, state) =>
                {
                    var sectionId = ToStringId(idParts(item.Item3));
                    parallelAction(item.Item1, item.Item3, state);
                    var measureResult = item.Item1.Measure.GetResults();
                    Safe.Lock(
                        serialLock,
                        Safe.MaxLockTimeout,
                        () =>
                    {
                        this.threadedMeasureResults.AddRange(item.Item1.ThreadedMeasureResults);
                        this.threadedMeasureResults.Add(new KeyValuePair <string, IEnumerable <TimeMeasureResult> >(sectionId, measureResult));
                        item.Item2.Flush();
                        done++;
                        if (done == parallelForEachItems.Count - 1)
                        {
                            parallelForEachItems.ForEach(i => i.Item2.Flush());
                        }
                    });
                });
            });
        }
コード例 #2
0
 /// <summary>Add resultsToAdd to results.</summary>
 /// <param name="resultsToAdd">The results To Add.</param>
 /// <param name="groupSelector">The group Selector.</param>
 /// <returns>The grouped result</returns>
 public static IEnumerable <TimeMeasureResult> Group(this IEnumerable <TimeMeasureResult> resultsToAdd, Func <TimeMeasureResult, string> groupSelector)
 {
     return
         (resultsToAdd
          .GroupBy(groupSelector)
          .Select(s => new TimeMeasureResult
     {
         IdParts = WebGreaseContext.ToIdParts(s.Key),
         Count = s.Min(m => m.Count),
         Duration = s.Sum(m => m.Duration)
     })
          .OrderByDescending(r => r.Duration)
          .ToArray());
 }
コード例 #3
0
 /// <summary>Gets the measure results for this timer.</summary>
 /// <returns>The measure results.</returns>
 public TimeMeasureResult[] GetResults()
 {
     return
         (this.measurements.Last().OrderByDescending(m => m.Value)
          .Select(
              m =>
              new TimeMeasureResult
     {
         IdParts = WebGreaseContext.ToIdParts(m.Key),
         Duration = m.Value,
         Count = this.measurementCounts.Last()[m.Key]
     })
          .ToArray());
 }
コード例 #4
0
ファイル: Program.cs プロジェクト: ymf1/webgrease
        /// <summary>The main entry point to the tool.</summary>
        /// <param name="args">The command line parameters.</param>
        /// <returns>The program result.</returns>
        internal static int Main(string[] args)
        {
            try
            {
                if (args == null || !args.Any())
                {
                    Console.WriteLine(ResourceStrings.Usage);
                    return(1);
                }

                WebGreaseConfiguration config;
                var mode    = GenerateConfiguration(args, out config);
                var context = new WebGreaseContext(config);

                switch (mode)
                {
                case ActivityMode.Minify:
                    ExecuteMinification(context);
                    break;

                case ActivityMode.Validate:
                    ExecuteValidation(context);
                    break;

                case ActivityMode.Bundle:
                    ExecuteBundling(context);
                    break;

                case ActivityMode.AutoName:
                    ExecuteHashFiles(context);
                    break;

                case ActivityMode.SpriteImages:
                    ExecuteImageSpriting(context);
                    break;

                default:
                    Console.WriteLine(ResourceStrings.Usage);
                    return(1);
                }
            }
            catch (Exception ex)
            {
                // general catch so unhandled exceptions don't result in a stack dump on the screen
                HandleError(ex, null, ResourceStrings.GeneralErrorMessage);
                return(-1);
            }

            return(0);
        }
コード例 #5
0
        /// <summary>Starts a new timer.</summary>
        /// <param name="isGroup">If it should also start a Group.</param>
        /// <param name="idParts">The id parts.</param>
        public void Start(bool isGroup, params string[] idParts)
        {
            var id = WebGreaseContext.ToStringId(idParts);

            if (this.timers.Any(t => t.Id.Equals(id)))
            {
                throw new BuildWorkflowException("An error occurred while starting timer for {0}, probably a wrong start/end for key: ".InvariantFormat(id));
            }

            this.PauseLastTimer();
            this.timers.Add(new TimeMeasureItem(id, DateTime.Now));

            if (isGroup)
            {
                this.BeginGroup();
            }
        }
コード例 #6
0
        /// <summary>Ends an already started timer.</summary>
        /// <param name="isGroup">if it is a group.</param>
        /// <param name="idParts">The id parts.</param>
        public void End(bool isGroup, params string[] idParts)
        {
            if (isGroup)
            {
                this.EndGroup();
            }

            var id        = WebGreaseContext.ToStringId(idParts);
            var lastTimer = this.timers.Last();

            if (lastTimer.Id != id)
            {
                throw new BuildWorkflowException("Trying to end a timer that was not started.");
            }

            this.StopTimer(lastTimer);
            this.ResumeLastTimer();
        }
コード例 #7
0
ファイル: WebGreaseSection.cs プロジェクト: ymf1/webgrease
        /// <summary>
        /// Executes the action for the cached section
        /// the boolean/success result of the action will determine if the action will be stored in cache.
        /// </summary>
        /// <param name="cachableSectionAction">The section action.</param>
        /// <returns>If all was successfull (being passed from within the actions).</returns>
        public bool Execute(Func <ICacheSection, bool> cachableSectionAction)
        {
            var id = WebGreaseContext.ToStringId(this.idParts);
            var webGreaseSectionKey = new WebGreaseSectionKey(this.context, id, this.cacheVarByContentItem, this.cacheVarBySetting, this.cacheVarByFileSet);
            var sectionLock         = SectionLocks.GetOrAdd(webGreaseSectionKey.Value, new object());

            return(Safe.Lock(
                       sectionLock,
                       this.cacheInfiniteWaitForLock ? Safe.MaxLockTimeout : Safe.DefaultLockTimeout,
                       () =>
            {
                var errorHasOccurred = false;
                EventHandler logOnErrorOccurred = delegate { errorHasOccurred = true; };
                this.context.Log.ErrorOccurred += logOnErrorOccurred;
                var cacheSection = this.context.Cache.BeginSection(webGreaseSectionKey);

                try
                {
                    if (this.context.TemporaryIgnore(this.cacheVarByFileSet, this.cacheVarByContentItem) && !errorHasOccurred)
                    {
                        cacheSection.Save();
                        return true;
                    }

                    cacheSection.Load();
                    if (this.cacheIsSkipable && cacheSection.CanBeSkipped())
                    {
                        if (this.whenSkippedAction != null)
                        {
                            this.whenSkippedAction(cacheSection);
                        }

                        if (!errorHasOccurred)
                        {
                            return true;
                        }
                    }

                    if (this.restoreFromCacheAction != null && cacheSection.CanBeRestoredFromCache())
                    {
                        if (this.restoreFromCacheAction(cacheSection) && !errorHasOccurred)
                        {
                            return true;
                        }
                    }

                    this.context.Measure.Start(this.isGroup, this.idParts);
                    try
                    {
                        if (!cachableSectionAction(cacheSection) || errorHasOccurred)
                        {
                            return false;
                        }

                        cacheSection.Save();
                        return true;
                    }
                    finally
                    {
                        this.context.Measure.End(this.isGroup, this.idParts);
                    }
                }
                finally
                {
                    this.context.Log.ErrorOccurred -= logOnErrorOccurred;
                    cacheSection.EndSection();
                }
            }));
        }