diff options
author | Kenneth Skovhede <kenneth@hexad.dk> | 2014-07-25 16:28:36 +0400 |
---|---|---|
committer | Kenneth Skovhede <kenneth@hexad.dk> | 2014-07-25 16:28:36 +0400 |
commit | c721a5fa9fd19cd1a42444d2b6b90f0fccea6a57 (patch) | |
tree | 5df0093fea868dfc1cda16d6eede67be9b138800 /Duplicati/Service | |
parent | 66f6e3a7ac6215b91bd6f0f388483bd98937072a (diff) |
Added the service component with basic polling functions
Diffstat (limited to 'Duplicati/Service')
4 files changed, 258 insertions, 0 deletions
diff --git a/Duplicati/Service/Duplicati.Service/Duplicati.Service.csproj b/Duplicati/Service/Duplicati.Service/Duplicati.Service.csproj new file mode 100644 index 000000000..9b0e827d2 --- /dev/null +++ b/Duplicati/Service/Duplicati.Service/Duplicati.Service.csproj @@ -0,0 +1,46 @@ +<?xml version="1.0" encoding="utf-8"?> +<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> + <PropertyGroup> + <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration> + <Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform> + <ProductVersion>8.0.30703</ProductVersion> + <SchemaVersion>2.0</SchemaVersion> + <ProjectGuid>{E93F3DE2-FF3A-4709-96A3-8190AA14FA25}</ProjectGuid> + <OutputType>Exe</OutputType> + <RootNamespace>Duplicati.Service</RootNamespace> + <AssemblyName>Duplicati.Service</AssemblyName> + </PropertyGroup> + <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' "> + <DebugSymbols>true</DebugSymbols> + <DebugType>full</DebugType> + <Optimize>false</Optimize> + <OutputPath>bin\Debug</OutputPath> + <DefineConstants>DEBUG;</DefineConstants> + <ErrorReport>prompt</ErrorReport> + <WarningLevel>4</WarningLevel> + <ConsolePause>false</ConsolePause> + </PropertyGroup> + <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' "> + <DebugType>full</DebugType> + <Optimize>true</Optimize> + <OutputPath>bin\Release</OutputPath> + <ErrorReport>prompt</ErrorReport> + <WarningLevel>4</WarningLevel> + <Externalconsole>true</Externalconsole> + </PropertyGroup> + <ItemGroup> + <Reference Include="System" /> + </ItemGroup> + <ItemGroup> + <Compile Include="Program.cs" /> + <Compile Include="Properties\AssemblyInfo.cs" /> + <Compile Include="Runner.cs" /> + </ItemGroup> + <Import Project="$(MSBuildBinPath)\Microsoft.CSharp.targets" /> + <ItemGroup> + <ProjectReference Include="..\..\Server\Duplicati.Server.csproj"> + <Project>{19E661D2-C5DA-4F35-B3EE-7586E5734B5F}</Project> + <Name>Duplicati.Server</Name> + </ProjectReference> + </ItemGroup> +</Project>
\ No newline at end of file diff --git a/Duplicati/Service/Duplicati.Service/Program.cs b/Duplicati/Service/Duplicati.Service/Program.cs new file mode 100644 index 000000000..844cd6767 --- /dev/null +++ b/Duplicati/Service/Duplicati.Service/Program.cs @@ -0,0 +1,31 @@ +// Copyright (C) 2014, Kenneth Skovhede
+
+// http://www.hexad.dk, opensource@hexad.dk
+//
+// This library is free software; you can redistribute it and/or modify
+// it under the terms of the GNU Lesser General Public License as
+// published by the Free Software Foundation; either version 2.1 of the
+// License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful, but
+// WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+using System;
+
+namespace Duplicati.Service
+{
+ class MainClass
+ {
+ public static void Main(string[] args)
+ {
+ using(var runner = new Runner())
+ runner.Wait();
+
+ }
+ }
+}
diff --git a/Duplicati/Service/Duplicati.Service/Properties/AssemblyInfo.cs b/Duplicati/Service/Duplicati.Service/Properties/AssemblyInfo.cs new file mode 100644 index 000000000..650f5a1e0 --- /dev/null +++ b/Duplicati/Service/Duplicati.Service/Properties/AssemblyInfo.cs @@ -0,0 +1,43 @@ +// Copyright (C) 2014, Kenneth Skovhede
+// http://www.hexad.dk, opensource@hexad.dk
+//
+// This library is free software; you can redistribute it and/or modify
+// it under the terms of the GNU Lesser General Public License as
+// published by the Free Software Foundation; either version 2.1 of the
+// License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful, but
+// WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+using System.Reflection;
+using System.Runtime.CompilerServices;
+
+// Information about this assembly is defined by the following attributes.
+// Change them to the values specific to your project.
+
+[assembly: AssemblyTitle("Duplicati.Service")]
+[assembly: AssemblyDescription("")]
+[assembly: AssemblyConfiguration("")]
+[assembly: AssemblyCompany("")]
+[assembly: AssemblyProduct("")]
+[assembly: AssemblyCopyright("")]
+[assembly: AssemblyTrademark("")]
+[assembly: AssemblyCulture("")]
+
+// The assembly version has the format "{Major}.{Minor}.{Build}.{Revision}".
+// The form "{Major}.{Minor}.*" will automatically update the build and revision,
+// and "{Major}.{Minor}.{Build}.*" will update just the revision.
+
+[assembly: AssemblyVersion("2.0.0.7")]
+
+// The following attributes are used to specify the signing key for the assembly,
+// if desired. See the Mono documentation for more information about signing.
+
+//[assembly: AssemblyDelaySign(false)]
+//[assembly: AssemblyKeyFile("")]
+
diff --git a/Duplicati/Service/Duplicati.Service/Runner.cs b/Duplicati/Service/Duplicati.Service/Runner.cs new file mode 100644 index 000000000..75a65066b --- /dev/null +++ b/Duplicati/Service/Duplicati.Service/Runner.cs @@ -0,0 +1,138 @@ +// Copyright (C) 2014, Kenneth Skovhede
+
+// http://www.hexad.dk, opensource@hexad.dk
+//
+// This library is free software; you can redistribute it and/or modify
+// it under the terms of the GNU Lesser General Public License as
+// published by the Free Software Foundation; either version 2.1 of the
+// License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful, but
+// WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+using System;
+
+namespace Duplicati.Service
+{
+ public class Runner : IDisposable
+ {
+ private System.Threading.Thread m_thread;
+ private volatile bool m_terminate = false;
+ private System.Diagnostics.Process m_process;
+
+ private readonly int WAIT_POLL_TIME = (int)TimeSpan.FromMinutes(15).TotalMilliseconds;
+
+ public Runner()
+ {
+ m_event = new System.Threading.ManualResetEvent(false);
+ m_thread = new System.Threading.Thread(Run);
+ m_thread.IsBackground = true;
+ m_thread.Name = "Server Runner";
+ m_thread.Start();
+ }
+
+ private void Run()
+ {
+ var self_exec = System.Reflection.Assembly.GetExecutingAssembly().Location;
+ var path = System.IO.Path.GetDirectoryName(System.Reflection.Assembly.GetExecutingAssembly().Location);
+ var exec = System.IO.Path.Combine(path, "Duplicati.Server.exe");
+ var cmdargs = Environment.CommandLine + " --ping-pong-keepalive=true";
+
+ if (cmdargs.StartsWith(self_exec))
+ cmdargs = cmdargs.Substring(self_exec.Length);
+
+
+ if (!System.IO.File.Exists(exec))
+ {
+ Console.WriteLine("File not found {0}", exec);
+ return;
+ }
+
+ while (!m_terminate)
+ {
+ try
+ {
+ var pr = new System.Diagnostics.ProcessStartInfo(exec, cmdargs);
+ pr.UseShellExecute = false;
+ pr.RedirectStandardInput = true;
+ pr.RedirectStandardOutput = true;
+
+ if (!m_terminate)
+ m_process = System.Diagnostics.Process.Start(pr);
+
+ while(!m_process.HasExited)
+ {
+ m_process.WaitForExit(WAIT_POLL_TIME);
+ if (!m_process.HasExited)
+ {
+ if (m_terminate)
+ m_process.Kill();
+ else
+ PingProcess();
+ }
+ }
+ }
+ catch (Exception ex)
+ {
+ Console.WriteLine(ex);
+
+ // Throttle restarts
+ if (!m_terminate)
+ System.Threading.Thread.Sleep(TimeSpan.FromSeconds(10));
+ }
+ }
+ }
+
+ private void PingProcess()
+ {
+ for(var n = 0; n < 5; n++)
+ {
+ m_process.StandardInput.WriteLine("ping");
+ m_process.StandardInput.Flush();
+
+ string msg = null;
+ System.Threading.ThreadPool.QueueUserWorkItem((x) =>
+ {
+ Console.WriteLine("Reading...");
+ msg = m_process.StandardOutput.ReadLine();
+ Console.WriteLine("Read: {0}", msg);
+ });
+
+ var i = 10;
+
+ while (string.IsNullOrWhiteSpace(msg) && i-- > 0)
+ System.Threading.Thread.Sleep(TimeSpan.FromSeconds(6));
+
+ if (!string.IsNullOrWhiteSpace(msg))
+ return;
+ }
+
+ throw new Exception("Process timed out!");
+ }
+
+ public void Wait()
+ {
+ m_thread.Join();
+ }
+
+ public void Stop()
+ {
+ m_terminate = true;
+ var p = m_process;
+ if (p != null)
+ p.Kill();
+ Wait();
+ }
+
+ public void Dispose()
+ {
+ Stop();
+ }
+ }
+}
+
|