具有多个参数的 WCF Restful API
WCF Restful API with multiple parameter
我正致力于在 VB.Net 中创建 WCF restful API,到目前为止,使用一个参数从 MSSQL 数据库获取数据并保存数据目前正在运行。
目前我正在尝试创建一个具有多个参数(电子邮件和密码)的服务合同来验证用户登录。这不断抛出以下错误,我只是不知道如何解决这个问题:
Error: Cannot obtain Metadata from localhost:12345/SMPCService.svc If this is a Windows (R) Communication Foundation service to which you have access, please check that you have enabled metadata publishing at the specified address. For help enabling metadata publishing, please refer to the MSDN documentation at go.microsoft.com/fwlink/?LinkId=65455.WS-Metadata Exchange Error URI: localhost:12345/SMPCService.svc Metadata contains a reference that cannot be resolved: localhost:12345/SMPCService.svc'. The requested service, 'localhost:12345/SMPCService.svc' could not be activated. See the server's diagnostic trace logs for more information.HTTP GET Error URI: localhost:12345/SMPCService.svc There was an error downloading '/localhost:12345/SMPCService.svc'. The request failed with the error message:--
这是我的服务合同:
<OperationContract()>
<WebInvoke(Method:="GET", ResponseFormat:=WebMessageFormat.Json, BodyStyle:=WebMessageBodyStyle.Wrapped, UriTemplate:="ValidateLogin/{e}/{p}")>
Function ValidateLogin(ByVal sEmailAddress As String, ByVal sPassword As String) As List(Of CheckLogin)
这是调用的 ValidateLogin 函数:
Public Function ValidateLogin(ByVal sEmailAddress As String, ByVal sPassword As String) As List(Of CheckLogin) Implements ISMPCService.ValidateLogin
Dim result As List(Of CheckLogin) = New List(Of CheckLogin)
Dim uAction = New CheckLogin
Dim pwd As String = ""
Try
' Dimension Local Variables
Dim uRecSnap As ADODB.Recordset
' Check For Open Connection
If uDBase Is Nothing Then
OpenConnection()
bConnection = True
End If
' Run Stored Procedure - Load Timesheet Record
uCommand = New ADODB.Command
With uCommand
.ActiveConnection = uDBase
.CommandType = ADODB.CommandTypeEnum.adCmdStoredProc
.CommandTimeout = 0
.Parameters.Append(.CreateParameter("@EmailAddress", ADODB.DataTypeEnum.adVarChar, ADODB.ParameterDirectionEnum.adParamInput, 30, sEmailAddress))
.CommandText = "API_WebUser_ValidateLogin"
uRecSnap = .Execute
End With
' Populate List
Do Until uRecSnap.EOF
pwd = If(IsDBNull(uRecSnap("UserPassword").Value), "", uRecSnap("UserPassword").Value)
uRecSnap.MoveNext()
Loop
uRecSnap = Nothing
If pwd <> "" Then
If pwd.Substring(0, 4) = "y$" Then
Mid(pwd, 3, 1) = "a"
End If
If BCrypt.Net.BCrypt.Verify(SHA512Hash(sPassword), pwd) Then
uAction.WasSuccessful = "OK"
uAction.StatusDescription = "User credentials match"
Else
uAction.WasSuccessful = "FAIL"
uAction.StatusDescription = "Failed to authorize user"
End If
Else
uAction.WasSuccessful = "FAIL"
uAction.StatusDescription = "Failed to authorize user"
End If
result.Add(uAction)
Catch ex As Exception
' Catch Error
If Err.Number <> 0 Then
Console.WriteLine(ex.Message)
End If
Finally
' CleanUp
' Close Database Connection
If bConnection Then CloseConnection()
End Try
Return result
End Function
最后,这是我的 Web.config:
<?xml version="1.0"?>
<configuration>
<appSettings>
<add key="aspnet:UseTaskFriendlySynchronizationContext" value="true" />
</appSettings>
<system.web>
<!--Disabled custom errors to allow display of detailed errors.-->
<customErrors mode="Off"/>
<compilation debug="true" strict="false" explicit="true" targetFramework="4.5" />
<httpRuntime targetFramework="4.5" relaxedUrlToFileSystemMapping="true"/>
</system.web>
<system.serviceModel>
<services>
<!--Specify services the application hosts.
Name specifies the type that provides an implementation of a service contract.
Behavior Configuration specifies the name of one of the behaviours found in the behaviours element and governs actions such as whether the service allows impersonation.-->
<service name="SMPCWebService.SMPCService" behaviorConfiguration="SMPCWebService.SMPCServiceBehaviour">
<!--Define the service endpoints.-->
<endpoint address="../SMPCService.svc" behaviorConfiguration="webBehaviour" binding="webHttpBinding" contract="SMPCWebService.ISMPCService" />
<endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange" />
</service>
</services>
<behaviors>
<serviceBehaviors>
<behavior name="SMPCWebService.SMPCServiceBehaviour">
<!-- To avoid disclosing metadata information, set the values below to false before deployment -->
<serviceMetadata httpGetEnabled="true"/>
<!-- To receive exception details in faults for debugging purposes, set the value below to true. Set to false before deployment to avoid disclosing exception information -->
<serviceDebug includeExceptionDetailInFaults="true" />
</behavior>
</serviceBehaviors>
<!--Define the endpoint behaviour.-->
<endpointBehaviors>
<behavior name="webBehaviour">
<webHttp />
</behavior>
</endpointBehaviors>
</behaviors>
<protocolMapping>
<add binding="basicHttpsBinding" scheme="https" />
</protocolMapping>
<serviceHostingEnvironment aspNetCompatibilityEnabled="true" multipleSiteBindingsEnabled="true" />
</system.serviceModel>
<system.webServer>
<!-- Allowing Cross-Origin Resource Sharing (CORS) - The httpProtocol settings allow web services to be called from external domains using JavaScript-->
<httpProtocol>
<customHeaders>
<add name="Access-Control-Allow-Origin" value="*" />
<add name="Access-Control-Allow-Headers" value="Content-Type, Accept" />
</customHeaders>
</httpProtocol>
<modules runAllManagedModulesForAllRequests="true"/>
<httpErrors errorMode="Detailed" />
<validation validateIntegratedModeConfiguration="false"/>
<!--
To browse web app root directory during debugging, set the value below to true.
Set to false before deployment to avoid disclosing web app folder information.
-->
<directoryBrowse enabled="true"/>
</system.webServer>
</configuration>
我查看了很多帖子以找到有关此事的提示,但我一无所获。
我看过的帖子:
Why do I get this WCF error when 'GET'ing?
Failed to add a service. Service metadata may not be accessible. Make sure your service is running and exposing metadata.`
How to send email address as parameter in wcf method
http://jeffbarnes.net/blog/post/2006/10/16/metadata-exchange-endpoint.aspx
在尝试了不同的方法后,我终于解决了错误的地方。
函数的参数名称需要与 UriTemplate 中指定的参数命名相同。
原文:
<OperationContract()>
<WebInvoke(Method:="GET", ResponseFormat:=WebMessageFormat.Json, BodyStyle:=WebMessageBodyStyle.Wrapped, UriTemplate:="ValidateLogin/{e}/{p}")>
Function ValidateLogin(ByVal sEmailAddress As String, ByVal sPassword As String) As List(Of CheckLogin)
修复:
<OperationContract()>
<WebInvoke(Method:="GET", ResponseFormat:=WebMessageFormat.Json, BodyStyle:=WebMessageBodyStyle.Wrapped, UriTemplate:="ValidateLogin/{e}/{p}")>
Function ValidateLogin(ByVal e As String, ByVal p As String) As List(Of CheckLogin)
我正致力于在 VB.Net 中创建 WCF restful API,到目前为止,使用一个参数从 MSSQL 数据库获取数据并保存数据目前正在运行。 目前我正在尝试创建一个具有多个参数(电子邮件和密码)的服务合同来验证用户登录。这不断抛出以下错误,我只是不知道如何解决这个问题:
Error: Cannot obtain Metadata from localhost:12345/SMPCService.svc If this is a Windows (R) Communication Foundation service to which you have access, please check that you have enabled metadata publishing at the specified address. For help enabling metadata publishing, please refer to the MSDN documentation at go.microsoft.com/fwlink/?LinkId=65455.WS-Metadata Exchange Error URI: localhost:12345/SMPCService.svc Metadata contains a reference that cannot be resolved: localhost:12345/SMPCService.svc'. The requested service, 'localhost:12345/SMPCService.svc' could not be activated. See the server's diagnostic trace logs for more information.HTTP GET Error URI: localhost:12345/SMPCService.svc There was an error downloading '/localhost:12345/SMPCService.svc'. The request failed with the error message:--
这是我的服务合同:
<OperationContract()>
<WebInvoke(Method:="GET", ResponseFormat:=WebMessageFormat.Json, BodyStyle:=WebMessageBodyStyle.Wrapped, UriTemplate:="ValidateLogin/{e}/{p}")>
Function ValidateLogin(ByVal sEmailAddress As String, ByVal sPassword As String) As List(Of CheckLogin)
这是调用的 ValidateLogin 函数:
Public Function ValidateLogin(ByVal sEmailAddress As String, ByVal sPassword As String) As List(Of CheckLogin) Implements ISMPCService.ValidateLogin
Dim result As List(Of CheckLogin) = New List(Of CheckLogin)
Dim uAction = New CheckLogin
Dim pwd As String = ""
Try
' Dimension Local Variables
Dim uRecSnap As ADODB.Recordset
' Check For Open Connection
If uDBase Is Nothing Then
OpenConnection()
bConnection = True
End If
' Run Stored Procedure - Load Timesheet Record
uCommand = New ADODB.Command
With uCommand
.ActiveConnection = uDBase
.CommandType = ADODB.CommandTypeEnum.adCmdStoredProc
.CommandTimeout = 0
.Parameters.Append(.CreateParameter("@EmailAddress", ADODB.DataTypeEnum.adVarChar, ADODB.ParameterDirectionEnum.adParamInput, 30, sEmailAddress))
.CommandText = "API_WebUser_ValidateLogin"
uRecSnap = .Execute
End With
' Populate List
Do Until uRecSnap.EOF
pwd = If(IsDBNull(uRecSnap("UserPassword").Value), "", uRecSnap("UserPassword").Value)
uRecSnap.MoveNext()
Loop
uRecSnap = Nothing
If pwd <> "" Then
If pwd.Substring(0, 4) = "y$" Then
Mid(pwd, 3, 1) = "a"
End If
If BCrypt.Net.BCrypt.Verify(SHA512Hash(sPassword), pwd) Then
uAction.WasSuccessful = "OK"
uAction.StatusDescription = "User credentials match"
Else
uAction.WasSuccessful = "FAIL"
uAction.StatusDescription = "Failed to authorize user"
End If
Else
uAction.WasSuccessful = "FAIL"
uAction.StatusDescription = "Failed to authorize user"
End If
result.Add(uAction)
Catch ex As Exception
' Catch Error
If Err.Number <> 0 Then
Console.WriteLine(ex.Message)
End If
Finally
' CleanUp
' Close Database Connection
If bConnection Then CloseConnection()
End Try
Return result
End Function
最后,这是我的 Web.config:
<?xml version="1.0"?>
<configuration>
<appSettings>
<add key="aspnet:UseTaskFriendlySynchronizationContext" value="true" />
</appSettings>
<system.web>
<!--Disabled custom errors to allow display of detailed errors.-->
<customErrors mode="Off"/>
<compilation debug="true" strict="false" explicit="true" targetFramework="4.5" />
<httpRuntime targetFramework="4.5" relaxedUrlToFileSystemMapping="true"/>
</system.web>
<system.serviceModel>
<services>
<!--Specify services the application hosts.
Name specifies the type that provides an implementation of a service contract.
Behavior Configuration specifies the name of one of the behaviours found in the behaviours element and governs actions such as whether the service allows impersonation.-->
<service name="SMPCWebService.SMPCService" behaviorConfiguration="SMPCWebService.SMPCServiceBehaviour">
<!--Define the service endpoints.-->
<endpoint address="../SMPCService.svc" behaviorConfiguration="webBehaviour" binding="webHttpBinding" contract="SMPCWebService.ISMPCService" />
<endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange" />
</service>
</services>
<behaviors>
<serviceBehaviors>
<behavior name="SMPCWebService.SMPCServiceBehaviour">
<!-- To avoid disclosing metadata information, set the values below to false before deployment -->
<serviceMetadata httpGetEnabled="true"/>
<!-- To receive exception details in faults for debugging purposes, set the value below to true. Set to false before deployment to avoid disclosing exception information -->
<serviceDebug includeExceptionDetailInFaults="true" />
</behavior>
</serviceBehaviors>
<!--Define the endpoint behaviour.-->
<endpointBehaviors>
<behavior name="webBehaviour">
<webHttp />
</behavior>
</endpointBehaviors>
</behaviors>
<protocolMapping>
<add binding="basicHttpsBinding" scheme="https" />
</protocolMapping>
<serviceHostingEnvironment aspNetCompatibilityEnabled="true" multipleSiteBindingsEnabled="true" />
</system.serviceModel>
<system.webServer>
<!-- Allowing Cross-Origin Resource Sharing (CORS) - The httpProtocol settings allow web services to be called from external domains using JavaScript-->
<httpProtocol>
<customHeaders>
<add name="Access-Control-Allow-Origin" value="*" />
<add name="Access-Control-Allow-Headers" value="Content-Type, Accept" />
</customHeaders>
</httpProtocol>
<modules runAllManagedModulesForAllRequests="true"/>
<httpErrors errorMode="Detailed" />
<validation validateIntegratedModeConfiguration="false"/>
<!--
To browse web app root directory during debugging, set the value below to true.
Set to false before deployment to avoid disclosing web app folder information.
-->
<directoryBrowse enabled="true"/>
</system.webServer>
</configuration>
我查看了很多帖子以找到有关此事的提示,但我一无所获。
我看过的帖子:
Why do I get this WCF error when 'GET'ing?
Failed to add a service. Service metadata may not be accessible. Make sure your service is running and exposing metadata.`
How to send email address as parameter in wcf method
http://jeffbarnes.net/blog/post/2006/10/16/metadata-exchange-endpoint.aspx
在尝试了不同的方法后,我终于解决了错误的地方。
函数的参数名称需要与 UriTemplate 中指定的参数命名相同。
原文:
<OperationContract()>
<WebInvoke(Method:="GET", ResponseFormat:=WebMessageFormat.Json, BodyStyle:=WebMessageBodyStyle.Wrapped, UriTemplate:="ValidateLogin/{e}/{p}")>
Function ValidateLogin(ByVal sEmailAddress As String, ByVal sPassword As String) As List(Of CheckLogin)
修复:
<OperationContract()>
<WebInvoke(Method:="GET", ResponseFormat:=WebMessageFormat.Json, BodyStyle:=WebMessageBodyStyle.Wrapped, UriTemplate:="ValidateLogin/{e}/{p}")>
Function ValidateLogin(ByVal e As String, ByVal p As String) As List(Of CheckLogin)