프로젝트

일반

사용자정보

통계
| 브랜치(Branch): | 개정판:

markus / ConvertService / ServiceBase / Markus.Service.Station / StationService / ServiceStationTask.cs @ 949d5058

이력 | 보기 | 이력해설 | 다운로드 (8.28 KB)

1 53c9637d taeseongkim
using Markus.Service.Interface;
2
using Markus.Message;
3
using System;
4
using System.Collections.Generic;
5
using System.Diagnostics;
6
using System.Linq;
7
using System.Text;
8
using System.Threading;
9
using System.Threading.Tasks;
10
using System.Management;
11
using static Markus.Service.Extensions.Encrypt;
12
using Markus.Service.Extensions;
13
using Markus.Service.Helper;
14
15
namespace Markus.Service
16
{
17
    /// <summary>
18
    /// 컨버터 큐 처리 
19
    /// </summary>
20
    public partial class ServiceStation
21
    {
22
        /// <summary>
23
        /// 컨버터 실행중인 item
24
        /// </summary>
25
        private static List<ConvertItem> AliveConvertQueue = new List<ConvertItem>();
26
27
        /// <summary>
28
        /// 컨버터 프로세스 실행
29
        /// </summary>
30
        /// <param name="convertitem"></param>
31
        public bool ConvertProcessStart(ConvertItem convertitem)
32
        {
33
            bool result = false;
34
            try
35
            {
36
           
37
                Process ConvertProcess = new Process();
38
39
                ProcessContext processSendData = new ProcessContext
40
                {
41
                    ConvertID = convertitem.ConvertID,
42
                    ConnectionString = MarkusDBConnectionString,
43
                    ServiceStationUri = gServiceHostAddress.ToString(),
44
                    OriginFilePath = convertitem.OriginfilePath,
45
                    SaveDirectory = convertitem.ConvertPath,
46
                    TempDirectory = DownloadTempFolder,
47
                    ReleaseWorkMemory = 1073741824,
48
                    MultiThreadMaxPages = MultiThreadMaxPages,
49
                    MinFontSize = MinFontSize,
50 2091a7e5 taeseongkim
                    SendStatusInterval = SaveStatusInterval,
51
                    UseResolution = UseResolution
52 53c9637d taeseongkim
                };
53
54
                var sendData = ObjectToBytesStringConvert.ObjectToBytesString(processSendData);
55
                
56
                ProcessStartInfo startInfo = new ProcessStartInfo
57
                {
58
                    UseShellExecute = false,
59
                    FileName = "Markus.Service.ConvertProcess.exe",
60
                    WindowStyle = ProcessWindowStyle.Hidden,
61
                    CreateNoWindow = true,
62
                    ErrorDialog = false,
63
                    RedirectStandardError = false,
64
                    Arguments = $"{convertitem.ConvertID.ToString()} {AESEncrypter.Encrypt(sendData)}"
65
                    //Arguments = $"{convertitem.ConvertID.ToString()} {convertitem.ProjectNumber} {AESEncrypter.Encrypt(MarkusDBConnectionString)} {gServiceHostAddress} {DownloadTempFolder} {MultiThreadMaxPages}"
66
                };
67
68
                ConvertProcess.StartInfo = startInfo;
69
                ConvertProcess.EnableRaisingEvents = false;
70
71
                System.Diagnostics.Debug.WriteLine("convert process run : " + startInfo.Arguments);
72
73
74
                if (ConvertProcess.Start())
75
                {
76
                    try
77
                    {
78
                        var processAffinity = ProcessorAffinityList.Except(AliveConvertQueue.Select(f => (long)f.ProcessorAffinity));
79
80
                        if (processAffinity.Count() > 0)
81
                        {
82
                            convertitem.ProcessorAffinity = processAffinity.First();
83
84
                            //int bitMask = 1 << (convertitem.ProcessorAffinity - 1);
85
                            //bitMask |= 1 << (anotherUserSelection - 1); / //  프로세스 두개 이상 선택
86
87
                            ConvertProcess.ProcessorAffinity = new IntPtr(convertitem.ProcessorAffinity);
88
89
                        }
90
                        else
91
                        {
92
                            // 모두 사용중일때 점유율이 작은 걸로 사용
93
                            var CurrentProcessAffinity = AliveConvertQueue.Select(f =>f.ProcessorAffinity).Distinct();
94
95
                            var affinity = CurrentProcessAffinity.Min();
96
97
                            convertitem.ProcessorAffinity = affinity;
98
                            ConvertProcess.ProcessorAffinity = new IntPtr(affinity);
99
                        }
100
                    }
101
                    catch (Exception ex)
102
                    {
103
                        System.Diagnostics.Debug.WriteLine(ex);
104
                    }
105
        
106
107
                    ServiceStation.AliveConvertQueue.Add(convertitem);
108
                    result = true;
109
                }
110
            }
111
            catch (Exception ex)
112
            {
113
                throw new Exception("ConvertThread " + $"{convertitem.ConvertID.ToString()} {convertitem.ProjectNumber} {AESEncrypter.Encrypt(MarkusDBConnectionString)} {gServiceHostAddress} {DownloadTempFolder} {MultiThreadMaxPages}", ex.InnerException);
114
            }
115
            finally
116
            {
117
                //GC.WaitForPendingFinalizers();
118
                //GC.Collect(2);
119
                //GC.Collect(2);
120
            }
121
122
            return result;
123
        }
124
125
        /// <summary>
126
        /// DB에 있는 대기중인 Item을 가져온다.
127
        /// </summary>
128
        public void setDataBaseWaitingList()
129
        {
130
            if (ServiceStation.AliveConvertQueue.Count() == 0)
131
            {
132
                /// 트랜젝션문제로 각각 선언하여 호출한다.
133
                using (DataBase.ConvertDatabase database = new DataBase.ConvertDatabase(MarkusDBConnectionString))
134
                {
135
                    database.SetCleanUpItems(RunProjectList);
136
                }
137
            }
138
139
            using (DataBase.ConvertDatabase database = new DataBase.ConvertDatabase(MarkusDBConnectionString))
140
            {
141
                var _items = database.GetWaitConvertItems(RunProjectList,ServiceStation.AliveConvertQueue, MultiProcessCount - ServiceStation.AliveConvertQueue.Count());
142
143
                if (_items.Count() > 0)
144
                {
145
                    foreach (var item in _items)
146
                    {
147
                        ConvertProcessStart(item);
148
                    }
149
                }
150
                else
151
                {
152
                    System.Diagnostics.Debug.WriteLine("");
153
                }
154
            }
155
        }
156
157
        public void Stopprocess()
158
        {
159
            var process = Process.GetProcessesByName("Markus.Service.ConvertProcess");
160
161
            for (int i = process.Count() - 1; i >= 0 ; i--)
162
            {
163
                try
164
                {
165
                    Console.WriteLine($"{i} Process Kill");
166
                    process[i].Kill();
167
                }
168
                catch (Exception ex)
169
                {
170
                    System.Diagnostics.Debug.WriteLine(ex.ToString());
171
                }
172
            }
173
        }
174
175
        /// <summary>
176
        /// finish가 호출되고 살아있는 프로세스라고 추정됨
177
        /// </summary>
178
        public void DeadLockProcessKill()
179
        {
180
            var process = Process.GetProcessesByName("Markus.Service.ConvertProcess");
181
182
            for (int i = process.Count() - 1; i >= 0; i--)
183
            {
184
                try
185
                {
186
                    var commandLines = process[i].Arguments().CommandLine;
187
188
                    if (commandLines.Count() > 0)
189
                    {
190
                        if (ServiceStation.AliveConvertQueue.Count(f => f.ConvertID == commandLines[0]) == 0)
191
                        {
192
                            process[i].Kill();
193
                        }
194
                    }
195
                }
196
                catch (Exception ex)
197
                {
198
                    System.Diagnostics.Debug.WriteLine(ex.ToString());
199
                }
200
            }
201
        }
202
203
        private void ConvertFinish(ConvertItem convertitem)
204
        {
205
            try
206
            {
207
                System.Diagnostics.Debug.WriteLine("Convert Finish : " + convertitem.ConvertID);
208
209
                System.Diagnostics.Debug.WriteLine("ServiceStation.AliveConvertQueue.Count() : " + ServiceStation.AliveConvertQueue.Count());
210
                
211
                ServiceStation.AliveConvertQueue.Remove(convertitem);
212
213
                System.Diagnostics.Debug.WriteLine("ServiceStation.AliveConvertQueue.Count() : " + ServiceStation.AliveConvertQueue.Count());
214
215
                if (ServiceStation.AliveConvertQueue.Count() < MultiProcessCount)
216
                {
217
                    setDataBaseWaitingList();
218
                }
219
            }
220
            catch (Exception ex)
221
            {
222
                logger.Error("ConvertFinish Error",ex);
223
            }
224
        }
225
    }
226
}
클립보드 이미지 추가 (최대 크기: 500 MB)