我正在开发一个ASP.NET(带有sql server)应用程序。我的要求是以特定的时间间隔从主机Web服务器(在我的情况下,来自Godaddy的Windows共享主机)发送电子邮件 - 这些可能是每天或每周或每月。无法使用Cron选项卡,因为它是在Linux主机上运行的Linux命令。 Godaddy的共享主机没有任何任务计划工具。我已经尝试了很多次但是无法获得成功。我已经使用过这三个代码。
首次尝试:
<%@ Application Language="C#" %>
<%@ Import Namespace="System.IO" %>
<%@ Import Namespace="System.Threading" %>
<%@ Import Namespace="System.Data" %>
<%@ Import Namespace="System.Data.SqlClient" %>
<%@ Import Namespace="System.Timers" %>
<script runat="server">
void Application_Start(object sender, EventArgs e)
{
// Code that runs on application startup
Thread timerThread = new Thread(TimerForNotification);
timerThread.IsBackground = true;
timerThread.Priority = ThreadPriority.Highest;
timerThread.Start();
}
void TimerForNotification()
{
//Code that runs on application startup
System.Timers.Timer timScheduledTask = new System.Timers.Timer();
timScheduledTask.Interval = 1000 * 60 * 60; //TimeSpan.FromMinutes(30).Minutes * 1000 * 60;
timScheduledTask.Enabled = true;
timScheduledTask.Elapsed += new System.Timers.ElapsedEventHandler(timScheduledTas_Elapsed);
}
void timScheduledTas_Elapsed(object sender, System.Timers.ElapsedEventArgs e)
{
ConnectionStringSettings conn = ConfigurationManager.ConnectionStrings["myshop_con"];
SqlConnection con = new SqlConnection(conn.ConnectionString);
SqlCommand cmd = con.CreateCommand();
cmd.CommandType = CommandType.Text;
cmd.CommandText = "insert into dbo.tblUserDetail(UName)VALUES('" + DateTime.Now.ToString() + "')";
con.Open();
cmd.ExecuteNonQuery();
con.Close();
}
</script>
第二次尝试:
<%@ Application Language="C#" %>
<%@ Import Namespace="System.IO" %>
<%@ Import Namespace="System.Threading" %>
<%@ Import Namespace="System.Data" %>
<%@ Import Namespace="System.Data.SqlClient" %>
<script runat="server">
public class TimerStarter
{
private static System.Threading.Timer threadingTimer;
public static void StartTimer()
{
if (null == threadingTimer)
{
threadingTimer = new System.Threading.Timer(new TimerCallback(DoActions), HttpContext.Current, 0, 3600000);
}
}
private static void DoActions(object sender)
{
ConnectionStringSettings conn = ConfigurationManager.ConnectionStrings["myshop_con"];
SqlConnection con = new SqlConnection(conn.ConnectionString);
SqlCommand cmd = con.CreateCommand();
cmd.CommandType = CommandType.Text;
cmd.CommandText = "insert into dbo.tblUserDetail(UName)VALUES('" + DateTime.Now.ToString() + "')";
con.Open();
cmd.ExecuteNonQuery();
con.Close();
}
}
void Application_Start(object sender, EventArgs e)
{
TimerStarter.StartTimer();
}
</script>
第三次尝试:
<%@ Application Language="C#" %>
<%@ Import Namespace="System.IO" %>
<%@ Import Namespace="System.Threading" %>
<%@ Import Namespace="System.Data" %>
<%@ Import Namespace="System.Data.SqlClient" %>
<script runat="server">
private void NightlyProcess(object o)
{
ConnectionStringSettings conn = ConfigurationManager.ConnectionStrings["myshop_con"];
SqlConnection con = new SqlConnection(conn.ConnectionString);
SqlCommand cmd = con.CreateCommand();
cmd.CommandType = CommandType.Text;
cmd.CommandText = "insert into dbo.tblUserDetail(UName)VALUES('" + DateTime.Now.ToString() + "')";
con.Open();
cmd.ExecuteNonQuery();
con.Close();
}
void Application_Start(object sender, EventArgs e)
{
System.Threading.TimerCallback tcb = new System.Threading.TimerCallback(NightlyProcess);
System.Threading.Timer theTimer = new System.Threading.Timer(tcb, null, GetTimerInitialDelay(20, 40), GetTimerRepeatDelay(24));
}
private long GetTimerInitialDelay(int hours, int minutes)
{
long startMS, repeatMS, currentMS;
startMS = (1000 * 60 * 60 * hours) + (1000 * 60 * minutes);
repeatMS = GetTimerRepeatDelay(24);
DateTime now = DateTime.Now;
long currentHours = 1000 * 60 * 60 * now.Hour;
long currentMinutes = 1000 * 60 * now.Minute;
long currentSeconds = 1000 * now.Second;
long currentMilliSeconds = now.Millisecond;
currentMS = currentHours + currentMinutes + currentSeconds + currentMilliSeconds;
long delay = startMS - currentMS;
if (delay < 0)
{
return repeatMS + delay;
}
else
{
return delay;
}
}
private long GetTimerRepeatDelay(int hours)
{
long repeatMS;
repeatMS = 1000 * 60 * 60 * hours;
return repeatMS;
}
</script>
如何以这些间隔发送这些电子邮件?
答案 0 :(得分:0)
如果没有在后台运行某种任务调度程序或Windows服务,您无法实现的目标。
您可以尝试做的是创建一个网页,当被请求时会发送一定数量的电子邮件,然后使用某些第三方ping服务或从本地PC运行的一些非常简单的脚本来调用此页面。
请注意,这只是一种解决方法,可靠的解决方案需要在具有VPS或专用服务器托管的服务器上进行更多访问。
您可以尝试的另一件事是某种第三方服务,它将为您发送电子邮件。你可以试试邮件黑猩猩 - 他们有免费版本,每月有限量的电子邮件,你也可以使用一个API。
答案 1 :(得分:0)
很老的问题,但可能会帮助一些新的读者。 在ASP.NET中,我们可以模拟Windows服务来运行预定作业。
这很奇怪,但缓存项目对于此目的非常有用。
逻辑非常简单而且不同。
创建缓存对象
private const string DummyCacheItemKey = "GagaGuguGigi";
protected void Application_Start(Object sender, EventArgs e)
{
RegisterCacheEntry();
}
private bool RegisterCacheEntry()
{
if( null != HttpContext.Current.Cache[ DummyCacheItemKey ] )
return false;
HttpContext.Current.Cache.Add( DummyCacheItemKey, "Test", null,
DateTime.MaxValue, TimeSpan.FromMinutes(1),
CacheItemPriority.Normal,
new CacheItemRemovedCallback( CacheItemRemovedCallback ) );
return true;
}
删除缓存对象后,引发回调函数以运行预定作业。
public void CacheItemRemovedCallback(string key,
object value, CacheItemRemovedReason reason)
{
Debug.WriteLine("Cache item callback: " + DateTime.Now.ToString() );
HitPage()
// Do the service works
DoWork();
}
在回调功能上,您必须再次设置缓存。为此,创建一个虚拟页面并通过webclient访问。
private const string DummyPageUrl =
"http://localhost/TestCacheTimeout/WebForm1.aspx";
private void HitPage()
{
WebClient client = new WebClient();
client.DownloadData(DummyPageUrl);
}
在Application_BeginRequest上检查它是否是虚拟页面。
protected void Application_BeginRequest(Object sender, EventArgs e)
{
// If the dummy page is hit, then it means we want to add another item
// in cache
if( HttpContext.Current.Request.Url.ToString() == DummyPageUrl )
{
// Add the item in cache and when succesful, do the work.
RegisterCacheEntry();
}
}
Here is the details how you can schedule your activities with pure ASP.NET