我正在开发Xamarin的PCL项目。我需要在web api Url中动态传递设备的IP地址。 我的代码如下:
在背后的代码中:
string IpAdd = txtIP.Text;
IPAddress = "http://" + IpAdd + ":8124/api/Items/";
MainViewModel.FinalIPAddress = IPAddress;
在我的MainViewModel
中public static string FinalIPAddress { get; set; }
public static readonly string WebServiceUrl = System.Net.WebUtility.UrlEncode(FinalIPAddress);
但我无法解决这个问题。抛出以下异常。
Exception thrown: 'System.InvalidOperationException' in System.Net.Http.Phone.ni.DLL
Additional information: An invalid request URI was provided. The request URI must either be an absolute URI or BaseAddress must be set.
如何解决这个问题?任何帮助将不胜感激。
答案 0 :(得分:0)
我认为模型实现中的WebServiceUrl看起来很奇怪。模型应该很薄。为什么不在您尝试使用WebServiceUrl并从模型中完全删除它时,在模型的FinalIPAddress上调用UrlEncode?
无论如何,在创建模型时,它可能没有FinalIPAddress的值,直到你分配它,所以它是空白的,你得到我想的例外。如果你想这样做,为什么不把它变成一个静态字符串函数而不是一个返回UrlEncode(FinalIPAddress)结果的变量。然后当你调用它时,可能在你填充了FinalIPAddress之后,它实时创建并且你得到了相同的结果。
此外,传统上在api中,您应该本地访问客户端的ip地址,该地址是来自请求本身和用户代理的请求。这可能是一种更精简的方法。
编辑:根据要求,实现此目的的最小代码更改将删除
public static readonly string WebServiceUrl = System.Net.WebUtility.UrlEncode(FinalIPAddress);
并用静态方法替换,你可以调用
public static string WebServiceUrl()
{
return System.Net.WebUtility.UrlEncode(FinalIPAddress);
}
然后像使用任何模型变量MainViewModel.WebServiceUrl()一样使用方法调用,并将其视为字符串。
有很多方法可以完成你想要做的事情,有些可以说是更好的做法。值得一读,但是现在这个小小的改变将使你的代码正常运行。
答案 1 :(得分:0)
以下代码可以解决您的问题。通常情况下,如果您只是指向您的api,则不会更改基址,但我不确定这里的最终目标是什么。
<强>模型强>
由于您计划对方案和路径进行硬编码,因此您只需要从用户输入中设置基址。
public class Model
{
public string BaseAddress { get; set; }
public string Scheme { get { return "http://"; } }
public string Path { get { return ":8124/api/Items"; } }
public string WebServiceURL {
get {
return Scheme + BaseAddress + Path;
}
}
}
<强>实施强>
我在这里创建了一个带有提交按钮的测试条目。
private Entry _urlEntry = new Entry { Placeholder = "url" };
private Button _submit = new Button { Text = "Submit" };
private Model _model;
public BackPage()
{
Content = new StackLayout
{
Children = { _urlEntry, _submit }
};
_submit.Clicked += Submit_Clicked;
}
按钮事件
你不必在这里实际模拟你的模型我只是不需要它来用于示例中的任何其他内容。
private void Submit_Clicked(object sender, System.EventArgs e)
{
var text = _urlEntry?.Text;
if(text.Length > 0)
{
_model = new Model { BaseAddress = text };
MakeRequest(_model.WebServiceURL);
}
else
{
DisplayAlert("Error", "Entry field is empty", "ok");
}
}
在此处提出要求
private void MakeRequest(string url)
{
}
<强>输出强>
在这里你可以看到,一旦你设置了Model.BaseAddress,你将拥有正确的&#34; FinalIPAdress&#34;你正在寻找。
答案 2 :(得分:0)
public static readonly string WebServiceUrl
删除'readonly',这应该适用于你的情况。