也谈MOSS控件中使用多语言

        今天看了博客园的RSS,看到 夏天的感觉写了关于MOSS国际化编程(多语言)的问题,春节前我在写一些通用控件时也遇到了一些问题,在这也分享一下。相同的我就不说了,我只说一下我不同的地方, 主要是关于部署的问题。
        首先,简单说说取资源的方法
        我建了两个资源文件,分别是 ResourceFileName.resx(默认使用英文), ResourceFileName.zh-ch.resx(中文),之所以不写 ResourceFileName.en-us.resx是因为当没有找到当前所需要的语言时,可以默认使用 ResourceFileName.resx文件。
        在取资源的时候,我选择使用了 HttpContext.GetGlobalResourceObject方法并把它包装在一个Helper类的静态方法里面,方便其它地方的调用,详细代码如下:
 1 /**/ /// <summary>
 2        /// 全局资源文件名
 3        /// </summary>

 4          internal   const   string  ResourceFileName  =   " ResourceFileName " ;
 5
 6 /**/ /// <summary>
 7        /// 返回全局资源
 8        /// </summary>
 9        /// <param name="key">资源关键字</param>
10        /// <returns></returns>

11          public   static   object  GetGlobalResource( string  key)
12          {
13            return GetGlobalResource(ResourceFileName, key);
14        }

15          /**/ /// <summary>
16        /// 返回全局资源
17        /// </summary>
18        /// <param name="resourceFileName">资源文件名</param>
19        /// <param name="key">资源关键字</param>
20        /// <returns></returns>

21          public   static   object  GetGlobalResource( string  resourceFileName,  string  key)
22          {
23            try
24            {
25                return HttpContext.GetGlobalResourceObject(resourceFileName, key, Thread.CurrentThread.CurrentCulture);
26            }

27            catch (Exception ex)
28            {
29                Log(ex.Message, EventLogEntryType.Warning);
30                return string.Empty;
31            }

32        }

调用时:
HelperClassName.GetGlobalResource( " KeyName " ).ToString();

第二,说说关于部署的问题
        在开发时,代码编译后把RESX文件与DLL拷到相应目录后就可以正常工作了,但由于我开发的是通用控件,不能使用手工部署,必须打包成WSP并在多个应用程序下都可以使用。恰恰是由于我写的resx文件是放在应用程序的App_GlobalResources文件夹下的,而打包成解决方案(wsp)的manifest并不支持把文件放到该文件夹下,当时我是打算改变取资源的方法,仅使用DLL文件形式的资源文件,因为dll文件我可以通过wsp部署到应用程序的bin或者GAC中,但最后考虑到使用起来的确不方便,还是放弃了这一想法,并集中火力,想方设法把文件拷到App_GlobalResources下。
        查阅了很多资料后,发现App_GlobalResources这个文件夹是在当应用程序建立时创建的(废话,嘻嘻),而App_GlobalResources文件夹里面的文件是从 “C:\Program Files\Common Files\Microsoft Shared\web server extensions\12\CONFIG\Resources”中拷贝过来的,而且仅当应用程序建立时才把文件全部拷贝过来,应用程序建立后,无论源文件夹怎样改变,应用程序的App_GlobalResources文件夹也不会得到同步。
        那么,wsp不能拷贝文件到App_GlobalResources下,源文件夹也不会自动与应用程序的App_GlobalResources同步,就是说MOSS本身是不支持App_GlobalResources下文件的部署的,而我们偏偏就需要部署文件到它下面。
经过上面的分析,我们可以做的事就只剩下一样的,利用eventhandler使用代码拷贝文件。要利用代码拷贝文件要考虑几件事情,首先是当wsp部署时要把文件拷贝过去,当wsp卸载时,要把文件删除;其次是当有多台前端服务器时要一起拷贝,一起删除。
        我在这里利用了MOSS的 SPJobDefinition类(从一个老外那查到的资料),把多台服务器一起执行的工作交给MOSS自己去处理 ,我们只要写做拷贝与删除的代码并写在SPJobDefinition中,在恰当的时候启动一个SPJob:
因为我是写一个通用控件,可以通过Feature来控件是启用该控件,当在启用该控件时,我便可以启动那个拷贝文件的SPJob类来拷贝需要的文件。

下面是详细的代码
1.从SPJobDefinition下继承下来的“拷贝文件工作类”:
 1 public   class  DeployGlobalResources : SPJobDefinition
 2      {
 3        Fields#region Fields
 4        [Persisted]
 5        private string sourcePath;
 6        #endregion

 7
 8        Constructors#region Constructors
 9        /**//// <summary>
10        /// Default constructor used by the system.
11        /// </summary>

12        public DeployGlobalResources() : base() { }
13
14
15        /**//// <summary>
16        /// Contructor used to create an instance, which deploys the resource files.
17        /// </summary>
18        /// <param name="WebApp">The SPWebApplication which needs to be updated</param>

19        public DeployGlobalResources(string jobName, SPWebApplication webApp, string featureName)
20            : base(jobName, webApp, null, SPJobLockType.Job)
21        {
22            // Detrmine the path to the feature's resource files
23            sourcePath = string.Format("{0}\\FEATURES\\{1}\\",
24                                        SPUtility.GetGenericSetupPath("Template"),
25                                        featureName);
26        }

27
28        #endregion

29
30        Job Handling#region Job Handling
31        /**//// <summary>
32        /// Called by OWSTIMER when the job runs on a server. Overriden from SPJobDefinition.
33        /// </summary>

34        public override void Execute(Guid targetInstanceId)
35        {
36            try
37            {
38                SPWebApplication webApp = this.Parent as SPWebApplication;
39
40                foreach (SPUrlZone zone in webApp.IisSettings.Keys)
41                {
42                    // The settings of the IIS application to update
43                    SPIisSettings oSettings = webApp.IisSettings[zone];
44
45                    // Determine the destination path
46                    string destPath = Path.Combine(oSettings.Path.ToString(), "App_GlobalResources");
47                    string[] filePaths = Directory.GetFiles(sourcePath, "*.resx");
48
49                    // Copy the files
50                    foreach (string filePath in filePaths)
51                    {
52                        string fileName = Path.GetFileName(filePath);
53                        File.Copy(filePath, Path.Combine(destPath, fileName), true);
54                    }

55                }

56            }

57            catch (Exception ex)
58            {
59                Debug.WriteLine("Failed to copy global resources");
60                Debug.WriteLine(ex);
61                throw;
62            }

63        }

64        #endregion

65    }
2. Feature的事件处理类
 1 public   class  GlobalResourcesEventReceiver : SPFeatureReceiver
 2      {
 3        Constants#region Constants
 4
 5        const string JOB_TITLE = "Deploy Global Resources";
 6        const string JOB_NAME = "job-deploy-global-resources";
 7
 8        #endregion

 9
10        Events#region Events
11
12        public override void FeatureActivated(SPFeatureReceiverProperties properties)
13        {
14            SPSite site = properties.Feature.Parent as SPSite;
15
16            // Check for an exising instance of the job
17            foreach (SPJobDefinition job in site.WebApplication.JobDefinitions)
18            {
19                if (job.Name == JOB_NAME && job.WebApplication.Name == site.WebApplication.Name)
20                {
21                    job.Delete();
22                }

23            }

24            // Create new job
25            DeployGlobalResources gsJob = new DeployGlobalResources(JOB_NAME, site.WebApplication, properties.Definition.DisplayName);
26            gsJob.Title = JOB_TITLE;
27            // Set up the job to run once
28            gsJob.Schedule = new SPOneTimeSchedule(DateTime.Now);
29            gsJob.Update();
30        }

31
32        public override void FeatureDeactivating(SPFeatureReceiverProperties properties)
33        {
34            SPSite site = properties.Feature.Parent as SPSite;
35
36            // delete the job
37            foreach (SPJobDefinition job in site.WebApplication.JobDefinitions)
38            {
39                if (job.Name == JOB_NAME &&
40                    job.WebApplication.Name == site.WebApplication.Name)
41                {
42                    job.Delete();
43                }

44            }

45            // Possibly delete the files on retract??
46        }

47
48        public override void FeatureInstalled(SPFeatureReceiverProperties properties)
49        {
50            //throw new Exception("The method or operation is not implemented.");
51        }

52
53        public override void FeatureUninstalling(SPFeatureReceiverProperties properties)
54        {
55            //throw new Exception("The method or operation is not implemented.");
56        }

57
58        #endregion

59    }

因为是项目的原因,只能把部分代码拷下来,其它的代码就不再详细说了,代码中也只写了拷贝文件,没写删除文件,只要根据提示加上相应的代码就行了。
另外,这是利用了MOSS的SPJOB来实现的,而spjob是使用wss的Timer服务调度的,在Feature启用时,文件的拷贝会有一定的延迟,默认延迟的时间不长,就几秒钟的时间。

转载于:https://www.cnblogs.com/davidluozw/archive/2008/02/15/1069223.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值