我要求我想要一个通过REST提供PDF的WCF服务库。
例如,我有一个这样的网址:localhost:8732/service1/reports/ok
我得到一个PDF作为回应。它是本地文件系统中的固定文件。
这是我目前的代码:
Service.cs
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Runtime.Serialization;
using System.ServiceModel;
using System.ServiceModel.Web;
using System.Text;
namespace WcfJsonRestService
{
// NOTE: You can use the "Rename" command on the "Refactor" menu to change the class name "Service1" in both code and config file together.
[ServiceBehavior(AddressFilterMode = AddressFilterMode.Any)]
public class Service1 : IService1
{
public Stream GetReport(string value)
{
WebOperationContext.Current.OutgoingResponse.ContentType = "application/pdf";
FileStream f = new FileStream("C:\\invoice.pdf", FileMode.Open);
int length = (int)f.Length;
WebOperationContext.Current.OutgoingResponse.ContentLength = length;
byte[] buffer = new byte[length];
int sum = 0;
int count;
while ((count = f.Read(buffer, sum, length - sum)) > 0)
{
sum += count;
}
f.Close();
return new MemoryStream(buffer);
}
}
}
IService.cs
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Runtime.Serialization;
using System.ServiceModel;
using System.ServiceModel.Web;
using System.Text;
namespace WcfJsonRestService
{
// NOTE: You can use the "Rename" command on the "Refactor" menu to change the interface name "IService1" in both code and config file together.
[ServiceContract]
public interface IService1
{
// TODO: Add your service operations here
[OperationContract(Action = "*")]
[WebInvoke(Method = "GET", //Este metodo si esta en POST, te dice que metodo no permitido
UriTemplate = "reports/{value}")]
Stream GetReport(string value);
}
// Use a data contract as illustrated in the sample below to add composite types to service operations.
// You can add XSD files into the project. After building the project, you can directly use the data types defined there, with the namespace "WcfJsonRestService.ContractType".
[DataContract]
public class CompositeType
{
bool boolValue = true;
string stringValue = "Hello ";
[DataMember]
public bool BoolValue
{
get { return boolValue; }
set { boolValue = value; }
}
[DataMember]
public string StringValue
{
get { return stringValue; }
set { stringValue = value; }
}
}
}
的App.config
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<system.serviceModel>
<services>
<service name="WcfJsonRestService.Service1">
<endpoint address="http://localhost:8732/service1"
binding="webHttpBinding"
contract="WcfJsonRestService.IService1"/>
</service>
</services>
<behaviors>
<endpointBehaviors>
<behavior>
<webHttp />
</behavior>
</endpointBehaviors>
</behaviors>
</system.serviceModel>
<startup>
<supportedRuntime version="v4.1" sku=".NETFramework,Version=v4.1"/>
</startup>
</configuration>
请不要注意那个误导性的名字&#34; WcfJsonRestService&#34;该名称将在以后更改为更合适的名称...
当我在Visual Studio 2013中运行时,一切都很好(除了来自Microsoft WCF服务主机的警告,它没有找到任何服务元数据)。当我访问http://localhost:8732/service1/somerandomstring时,浏览器会打开pdf。 (请注意,目前我的文件系统上是一个固定的目录......)
问题出在我尝试发布或托管时。我跟着几个关于在IIS中托管的教程没有成功。 我该怎样做才能使这个工作?
操作系统:Windows 8.1 .NET Framework 4
答案 0 :(得分:1)
我试图在我的机器上填充问题而且我得到了它。我也找到了解决方案。在IIS中托管后。您访问该服务的网址为http://localhost/<name of the site while hosting to iis>/<namespaceofyourservice>.<servicename>/<method name>
。
所以我的情况就变成了http://localhost/WcfJSONPDF/WcfJsonRestService.Service1.svc/reports/ok
。在这里&#34; ok&#34;是传递给Web方法的字符串。
我知道奇怪的是我们必须在url中传递名称空间,但你现在必须接受它。我会寻找一些解决方法。以下是网址定义的图片:。
以下是将Wcf Service Library
项目发布到IIS7的步骤。请参见下图:
Click on Build-->Publish Webservice-->Name the url(website name)-->Click on publish button-->Click publish on Local IIS
。
多数民众赞成。我希望您能获得所需的输出。
如果您仍然遇到问题,请使用以下内容更新App.config
:
<?xml version="1.0"?>
<configuration>
<system.serviceModel>
<services>
<service name="WcfJsonRestService.Service1" behaviorConfiguration="Metadata">
<endpoint address=""
binding="webHttpBinding"
contract="WcfJsonRestService.IService1" behaviorConfiguration="Restbeh"/>
<endpoint name="mex"
address="mex"
binding="mexHttpBinding"
contract="IMetadataExchange" />
<host>
<baseAddresses>
<add baseAddress="http://localhost:80/service1" />
</baseAddresses>
</host>
</service>
</services>
<behaviors>
<endpointBehaviors>
<behavior name="Restbeh">
<webHttp />
</behavior>
</endpointBehaviors>
<serviceBehaviors>
<behavior name="Metadata">
<serviceMetadata httpGetEnabled="true" />
</behavior>
</serviceBehaviors>
</behaviors>
</system.serviceModel>
<startup>
<supportedRuntime version="v4.1" sku=".NETFramework,Version=v4.1"/>
</startup>
</configuration>
答案 1 :(得分:1)
几天前我偶然发现了这个问题:这是由于缺少处理程序映射,这是处理这种类型的调用所必需的。有几种方法可以解决此问题,例如手动执行ServiceModelReg.exe
控制台命令。我在下面提出的解决方法比较复杂,但它的优点是可以在不改变Web服务器默认行为的情况下修复特定问题,从而减少潜在的副作用。
安装完成后,您应该能够运行WCF服务而不会再次发生404错误。
有关此特定问题以及如何解决此问题的其他信息,您还可以在我的博客上read this post。
答案 2 :(得分:0)
可能是权限问题,在IIS中托管时,您需要为您的网站在该文件夹及其内容下运行的标识提供读取权限。您正在运行的身份取决于您使用的IIS版本以及您如何配置应用池。您可以通过查看应用池的高级设置并向下滚动到标识来检查它的身份。然后检查pdf文件夹中的安全设置以供该用户使用。