%temp%对ASP.NET有什么用?

今天遇到一个问题, 客户站点上的所有的web part都显示一个错误信息:

Web Part Error: One of the properties of the Web Part has an incorrect format. Windows SharePoint Services cannot deserialize the Web Part. Check the format of the properties and try again.

最后通过给%temp%文件夹赋予必要的权限而解决.

是什么样的权限呢? 答: 进程账户必须拥有读, 写, 删除的权限. 信息来源: Building Secure ASP.NET Applications: Authentication, Authorization, and Secure Communication

更深入一点想, 为什么%temp%会影响到ASP.NET中的web part的显示呢?

最想先想到的是%SystemRoot%\Microsoft.NET\Framework\versionNumber\Temporary ASP.NET Files 这个文件夹, 它是ASP.NET动态编译的地方. 关于这个话题, 可以参考Understanding ASP.NET Dynamic Compilation. 但这并不是%temp%指向的文件夹呀.

Google一下, 发现%temp%文件夹是被Web services生成序列化所需要的代理(proxies)的地方. 难怪错误信息中会有web part无法被反序列化这样的字眼了. 信息来源: Building Secure ASP.NET Applications: Authentication, Authorization, and Secure Communication.

原文为: This is the location used by Web services to generate serialization proxies.

那么什么是Serialization呢?

Serialization can be defined as the process of storing the state of an object instance to a storage medium. During this process, the public and private fields of the object and the name of the class, including the assembly containing the class, is converted to a stream of bytes, which is then written to a data stream. When the object is subsequently deserialized, an exact clone of the original object is created.

The Common Language Runtime (CLR) manages how objects are laid out in memory and the .NET Framework provides an automated serialization mechanism by using reflection.

Objects often store references to other instances in member variables. When the class is serialized, the serialization engine keeps track of all referenced objects already serialized to ensure that the same object is not serialized more than once.

The only requirement placed on object graphs is that all objects referenced by the object that is being serialized must also be marked as Serializable (see Basic Serialization). If this is not done, an exception will be thrown when the serializer attempts to serialize the unmarked object.

Objects are only valid in the application domain where they are created. Any attempt to pass the object as a parameter or return it as a result will fail unless the object derives from MarshalByRefObject or is marked as Serializable. If the object is marked as Serializable, the object will automatically be serialized, transported from the one application domain to the other, and then deserialized to produce an exact copy of the object in the second application domain. This process is typically referred to as marshal by value.

注意, 下面这段话引出了Proxy.

When an object derives from MarshalByRefObject, an object reference will be passed from one application domain to another, rather than the object itself. You can also mark an object that derives from MarshalByRefObject as Serializable. When this object is used with remoting, the formatter responsible for serialization, which has been preconfigured with a SurrogateSelector takes control of the serialization process and replaces all objects derived from MarshalByRefObject with a proxy.

It is important to note that the Serializable attribute cannot be inherited. If we derive a new class from MyObject, the new class must be marked with the attribute as well, or it cannot be serialized.

以上内容来自Object Serialization in the .NET Framework

综合以上信息, 其过程应该是这样的, ASP.NET产生出了webpart, 由于webpart仅在创建它的appdomain里是合法的, 在将它传给WSS service的时候, 必须经过序列化. 而序列化需要WSS service产生序列化代理, 这个产生的位置就在系统环境变量的%temp%中, 默认情况下是C:\Windows\TEMP. 如果运行进程的账户没有这个文件夹的读写删权限, 就会报出上面的错误.

原文地址:https://www.cnblogs.com/awpatp/p/1634388.html