Web应用服务器端定时任务问题

kirawoo 2015-07-09 03:00:35
功能: 开发一个WEB应用,服务器端设定一个定时器,定时发送邮件和记录log。

网上找到在WEB应用中新建Global.asax文件,在里面的void Application_Start(object sender, EventArgs e) 方法中加入定时器,来实现WEB应用定时功能,如下代码。网站被访问一次后,定时器就一直不停的在运行,现在问题是这样的:web应用在用VS调试的时候能正常运行,在发布到网站后安装到后台服务器上后,邮件能定时发送出来,但写log不能定时写入,查看log文件中没有写入记录。请高手帮忙指导一下,为什么会这样啊??

////////////Global.asax文件//////////////////////////////////////
<%@ Application Language="C#" %>

<script runat="server">

void Application_Start(object sender, EventArgs e)
{
//在应用程序启动时运行的代码
System.Timers.Timer xlstimer = new System.Timers.Timer(60500);//一分钟执行一次,单位为毫秒
xlstimer.Elapsed += new System.Timers.ElapsedEventHandler(xlstimer_Elapsed);
xlstimer.AutoReset = true; //为False只执行一次
xlstimer.Enabled = true; //为True启动定时器

}

void Application_End(object sender, EventArgs e)
{
//在应用程序关闭时运行的代码

}

void Application_Error(object sender, EventArgs e)
{
//在出现未处理的错误时运行的代码

}

void Session_Start(object sender, EventArgs e)
{
//在新会话启动时运行的代码

}

void Session_End(object sender, EventArgs e)
{
//在会话结束时运行的代码。
// 注意: 只有在 Web.config 文件中的 sessionstate 模式设置为
// InProc 时,才会引发 Session_End 事件。如果会话模式
//设置为 StateServer 或 SQLServer,则不会引发该事件。

}

protected void xlstimer_Elapsed(object sender, System.Timers.ElapsedEventArgs e)
{
//邮件发送代码
CEMail email = new CEMail();
email.send();
//写LOG文件内容
System.IO.StreamWriter sw = System.IO.File.AppendText("C:/log/" + DateTime.Now.ToString("yyyyMMdd") + ".Log");
sw.WriteLine(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss: ") + "Warning" + "-" + "aaa");
sw.Close();
}

</script>
...全文
309 8 打赏 收藏 转发到动态 举报
写回复
用AI写文章
8 条回复
切换为时间正序
请发表友善的回复…
发表回复
yinlu5215211 2015-07-10
  • 打赏
  • 举报
回复
在服务器开始的时候就开始每分钟发送邮件 负载的问题是该考虑,不错收下了
myhope88 2015-07-10
  • 打赏
  • 举报
回复
可能没目录操作权限吧,检查下
kirawoo 2015-07-10
  • 打赏
  • 举报
回复
多谢各位的提点,我找到的log文件不能写入的原因,还是各位说的访问权限的问题,只需要更改对应web应用的“应用程序池”的权限,如果使用的是默认应用程序池,那么就是“DefaultAppPool”,在“DefaultAppPool”上面右击→属性→标识选项卡→预定义账户,默认是“网络服务”改成“本地系统”,但是更改的时候系统提示不安全。

有一个问题,各位你们对这个“应用程序池”的账户设置是否有经验,里面“预定义账户”中的“网络服务”、“本地服务”、“本地系统”有什么区别?为什么系统默认选择的“网络服务”就不能文件写入?谁有关于“应用程序池”账户权限这方面的介绍?

附:我用的win2003+iis6
  • 打赏
  • 举报
回复
CreateDir(dir) 方法自己实现吧,就是检查目录是否存在、如果不存在则创建目录。
  • 打赏
  • 举报
回复
Log信息不要“定时写入”。这个时间,你设置得长也不是、短也不是,就是个鸡肋。 为了cpu负载均衡,那么应该使用系统线程池来自动对任务进行智能调度。可以这样记录日志
private static object WriteLogFlag = new object();
private static int AsyncWritelogHold = 20;
private static int AsyncWriteLogCount = 0;

public static void WriteLogToFileSystem(string className, object message, EventLogEntryType type)
{
    lock (WriteLogFlag)
    {
        if (AsyncWriteLogCount >= AsyncWritelogHold)
        {
            WriteLogToFileSystem2("WriteLogToFileSystem", new { _ = "消息积压", AsyncWriteLogCount, AsyncWritelogHold }, EventLogEntryType.Warning);
            return;     //丢掉日志具体内容,节省时间
        }

        ++AsyncWriteLogCount;
    }
    WriteLogToFileSystem2(className, message, type);
}

private static void WriteLogToFileSystem2(string className, object message, EventLogEntryType type)
{
    var content = GetEventString(message);  //无法确保对象引用message不被修改,因此此语据不能异步处理
    var dir = new DirectoryInfo(Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "Log", DateTime.Now.ToString("yyyy_MM_dd")));
    var file = new FileInfo(Path.Combine(dir.FullName, className + "_" + type.ToString() + ".txt"));
    var sp = new string('-', 20);
    var msg = string.Format("{0} {1} {0}\r\n\r\n{2}\r\n\r\n", sp, DateTime.Now.ToString("HH:mm:ss.fff"), content);
    ThreadPool.QueueUserWorkItem(h =>
    {
        lock (WriteLogFlag)
        {
            --AsyncWriteLogCount;
            CreateDir(dir);
            using (var fw = file.Open(FileMode.Append, FileAccess.Write))
            using (var sw = new StreamWriter(fw))
            {
                sw.Write(msg);
                sw.Close();
            }
        }
    });
}

private static string GetEventString(object message)
{
    string msg;
    if (message is Exception || message is string)
        msg = message.ToString();
    else
    {
        try
        {
            msg = JToken.FromObject(message).ToString();
        }
        catch
        {
            msg = message.ToString();
        }
    }
    return msg;
}

}
江南小鱼 2015-07-09
  • 打赏
  • 举报
回复
1、先判断日志文件是否存在,如果不存在创建,否则追加

if (!File.Exists(path))
                {
                    using (FileStream fileStream = File.Create(path))
                    {
                        byte[] bytes = new UTF8Encoding(true).GetBytes(text + "\r\n");
                        fileStream.Write(bytes, 0, bytes.Length);
                    }
                }
                else
                {
                    using (StreamWriter streamWriter = new StreamWriter(path, true))
                    {
                        streamWriter.WriteLine(text);
                    }
                }
2、确定服务器C盘是否有权限写文件
江南小鱼 2015-07-09
  • 打赏
  • 举报
回复
晕~ 你直接AppendText,日志文件谁创建?
江南小鱼 2015-07-09
  • 打赏
  • 举报
回复

try
{//写LOG文件内容
        System.IO.StreamWriter sw = System.IO.File.AppendText("C:/log/" + DateTime.Now.ToString("yyyyMMdd") + ".Log");
         sw.WriteLine(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss: ") + "Warning" + "-" + "aaa");
         sw.Close();
}
catch(Exceptionex)
{
//记录下来
}
加上try catch,看这段代码是否抛出异常? C盘是否没有写入权限?

62,074

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术交流专区
javascript云原生 企业社区
社区管理员
  • ASP.NET
  • .Net开发者社区
  • R小R
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

.NET 社区是一个围绕开源 .NET 的开放、热情、创新、包容的技术社区。社区致力于为广大 .NET 爱好者提供一个良好的知识共享、协同互助的 .NET 技术交流环境。我们尊重不同意见,支持健康理性的辩论和互动,反对歧视和攻击。

希望和大家一起共同营造一个活跃、友好的社区氛围。

试试用AI创作助手写篇文章吧