278 lines
8.7 KiB
C#
278 lines
8.7 KiB
C#
//////////////////////////////////////////////////////////////////////////
|
||
//
|
||
// 文件:Assets/Code/Scripts/Gameplay/Net/Client/AppConfig.cs
|
||
// 作者:Xoen Xie
|
||
// 时间:2023/07/19
|
||
// 描述:app config
|
||
// 说明:
|
||
//
|
||
//////////////////////////////////////////////////////////////////////////
|
||
|
||
using Framework;
|
||
using UnityEngine;
|
||
using System.Collections.Generic;
|
||
using UnityEngine.Networking;
|
||
using System.Xml;
|
||
using System;
|
||
using System.IO;
|
||
using System.Text;
|
||
using Cysharp.Threading.Tasks;
|
||
using PhxhSDK;
|
||
|
||
namespace Gameplay.Net
|
||
{
|
||
public struct AddrInfo
|
||
{
|
||
public string ip;
|
||
public uint port;
|
||
}
|
||
|
||
public struct ServerInfo
|
||
{
|
||
public string name;
|
||
|
||
public AddrInfo[] addrs;
|
||
}
|
||
|
||
public class CompulsoryUpdate
|
||
{
|
||
public bool NeedUpdate;
|
||
public Dictionary<string, string> AppUrl;
|
||
}
|
||
|
||
public class NoticeInfo
|
||
{
|
||
public string Title;
|
||
public string Content;
|
||
}
|
||
|
||
public interface IAppConfigHandler
|
||
{
|
||
void OnAppConfigDone();
|
||
}
|
||
|
||
public sealed class AppConfig : Singlenton<AppConfig>, IInitable
|
||
{
|
||
#if UNITY_EDITOR
|
||
private readonly string appDir = "editor";
|
||
#elif UNITY_ANDROID
|
||
private readonly string appDir = "android";
|
||
#elif UNITY_IOS
|
||
private readonly string appDir = "ios";
|
||
#else
|
||
private readonly string appDir = "other";
|
||
#endif
|
||
|
||
private readonly string
|
||
appURLPrefix = "http://132.232.113.98/config/"; // editor/server.0.0.1.xml";
|
||
|
||
private string m_sAppUrl;
|
||
|
||
private List<ServerInfo> m_ServerInfos;
|
||
|
||
|
||
public CompulsoryUpdate UpdateInfo { get; private set; }
|
||
|
||
public List<NoticeInfo> NoticeInfos { get; private set; }
|
||
|
||
public ServerInfo Current { get; private set; }
|
||
|
||
public void Init()
|
||
{
|
||
string version = Application.version;
|
||
DebugUtil.Log("AppConfig Current App Version:{0}", version);
|
||
|
||
m_sAppUrl = $"{appURLPrefix}/{appDir}/server.{version}.xml";
|
||
DebugUtil.Log("AppConfig Current App Config Url:{0}", m_sAppUrl);
|
||
|
||
m_ServerInfos = new List<ServerInfo>();
|
||
}
|
||
|
||
public List<ServerInfo> GetServerInfo()
|
||
{
|
||
return m_ServerInfos;
|
||
}
|
||
|
||
public ServerInfo GetCurrent()
|
||
{
|
||
return Current;
|
||
}
|
||
|
||
public void Release()
|
||
{
|
||
}
|
||
|
||
public async UniTask<bool> UnityRequest()
|
||
{
|
||
try
|
||
{
|
||
DebugUtil.Log("AppConfig Request url={0}", m_sAppUrl);
|
||
|
||
var request = UnityWebRequest.Get(m_sAppUrl);
|
||
|
||
await request.SendWebRequest();
|
||
|
||
OnRequestFinished(request);
|
||
|
||
if (m_ServerInfos == null)
|
||
{
|
||
DebugUtil.LogError("request---------- serverInfo = null");
|
||
return false;
|
||
}
|
||
|
||
return true;
|
||
}
|
||
catch (Exception e)
|
||
{
|
||
DebugUtil.LogError(e);
|
||
return false;
|
||
}
|
||
}
|
||
|
||
|
||
private IAppConfigHandler m_handler;
|
||
|
||
public async UniTask RequestWithCallback(IAppConfigHandler h)
|
||
{
|
||
m_handler = h;
|
||
//HTTPRequest request = new HTTPRequest(new Uri(m_sAppUrl), OnRequestFinished);
|
||
//request.Send();
|
||
|
||
var request = UnityWebRequest.Get(m_sAppUrl);
|
||
await request.SendWebRequest();
|
||
OnRequestFinished(request);
|
||
}
|
||
|
||
void OnRequestFinished(UnityWebRequest request)
|
||
{
|
||
switch (request.result)
|
||
{
|
||
// The request finished without any problem.
|
||
case UnityWebRequest.Result.Success:
|
||
OnServerInfo(request.downloadHandler.text);
|
||
if (m_handler != null)
|
||
{
|
||
m_handler.OnAppConfigDone();
|
||
}
|
||
break;
|
||
case UnityWebRequest.Result.ConnectionError:
|
||
// TODO, retry several times
|
||
DebugUtil.LogError("Request Finished with Error, error = {0} ", request.error);
|
||
break;
|
||
case UnityWebRequest.Result.ProtocolError:
|
||
// TODO, version error
|
||
DebugUtil.LogError("Request Finished with Error, error = {0} ", request.error);
|
||
break;
|
||
case UnityWebRequest.Result.DataProcessingError:
|
||
// TODO, version error
|
||
DebugUtil.LogError("Request Finished with Error, error = {0} ", request.error);
|
||
break;
|
||
default:
|
||
DebugUtil.LogError("Request Finished with Error, error = {0} ", request.error);
|
||
break;
|
||
}
|
||
}
|
||
|
||
private void OnServerInfo(string text)
|
||
{
|
||
var settings = new XmlReaderSettings();
|
||
settings.IgnoreComments = true;
|
||
|
||
var reader = XmlReader.Create(new MemoryStream(Encoding.UTF8.GetBytes(text)), settings);
|
||
var doc = new XmlDocument();
|
||
doc.Load(reader);
|
||
|
||
//获取强更信息
|
||
UpdateInfo = new CompulsoryUpdate();
|
||
var configNode = doc.SelectSingleNode("root/config");
|
||
UpdateInfo.NeedUpdate = bool.Parse(configNode.SelectSingleNode("AppUpdate").InnerText);
|
||
DebugUtil.Log("Need to force update:{0}", UpdateInfo.NeedUpdate);
|
||
|
||
if (UpdateInfo.NeedUpdate)
|
||
{
|
||
OpenNeedUpdateWindows();
|
||
return;
|
||
}
|
||
|
||
var appUrls = configNode.SelectNodes("AppUrl/u");
|
||
UpdateInfo.AppUrl = new Dictionary<string, string>();
|
||
foreach (XmlNode urlNode in appUrls)
|
||
{
|
||
string type = urlNode.Attributes["type"].Value;
|
||
string data = urlNode.Attributes["data"].Value;
|
||
UpdateInfo.AppUrl.Add(type, data);
|
||
}
|
||
|
||
//获取公告信息
|
||
NoticeInfos = new List<NoticeInfo>();
|
||
var noticeNode = doc.SelectSingleNode("root/notice");
|
||
if (noticeNode != null)
|
||
{
|
||
var noticeList = noticeNode.ChildNodes;
|
||
for (int i = 0; i < noticeList.Count; i++)
|
||
{
|
||
var noticeElement = noticeList[i] as XmlElement;
|
||
NoticeInfo noticeInfo = new NoticeInfo();
|
||
noticeInfo.Title = noticeElement.SelectSingleNode("title").InnerText;
|
||
noticeInfo.Content = noticeElement.SelectSingleNode("body").InnerText;
|
||
NoticeInfos.Add(noticeInfo);
|
||
}
|
||
}
|
||
|
||
var rootNode = doc.SelectSingleNode("root");
|
||
var nodeList = rootNode.SelectSingleNode("ServerList").ChildNodes;
|
||
for (var i = 0; i < nodeList.Count; ++i)
|
||
{
|
||
var ele = nodeList[i] as XmlElement;
|
||
|
||
ServerInfo sni;
|
||
sni.name = ele.GetAttribute("name");
|
||
sni.addrs = new AddrInfo[ele.ChildNodes.Count];
|
||
|
||
for (var J = 0; J < ele.ChildNodes.Count; J++)
|
||
{
|
||
var eleAddr = ele.ChildNodes[J] as XmlElement;
|
||
AddrInfo adi;
|
||
adi.ip = eleAddr.GetAttribute("ip");
|
||
string port = eleAddr.GetAttribute("port");
|
||
adi.port = Convert.ToUInt32(port);
|
||
sni.addrs[J] = adi;
|
||
}
|
||
|
||
foreach (var info in NoticeInfos)
|
||
{
|
||
DebugUtil.Log("AppConfig.NoticeInfo Title={0},Content={1}", info.Title, info.Content);
|
||
}
|
||
|
||
DebugUtil.Log("AppConfig.OnServerInfo name={0}, count={1} ip={2}, port={3}",
|
||
sni.name, sni.addrs.Length, sni.addrs[0].ip, sni.addrs[0].port);
|
||
|
||
m_ServerInfos.Add(sni);
|
||
}
|
||
|
||
if (EventManager.Instance != null)
|
||
EventManager.Instance.Send(EventManager.EventName.NetLoginServerInfo);
|
||
}
|
||
|
||
|
||
public void Select(int nIndex)
|
||
{
|
||
if (nIndex >= m_ServerInfos.Count)
|
||
{
|
||
Current = m_ServerInfos[0];
|
||
DebugUtil.LogError("AppConfig Select nIndex:{0} >= m_ServerInfos.Count:{1}, set default as 0", nIndex,
|
||
m_ServerInfos.Count);
|
||
return;
|
||
}
|
||
|
||
Current = m_ServerInfos[nIndex];
|
||
DebugUtil.Log("AppConfig Select name={0}, length={1}", Current.name, Current.addrs.Length);
|
||
}
|
||
|
||
private void OpenNeedUpdateWindows()
|
||
{
|
||
UIManager.Instance.OpenWindow(UINameConst.UI_Update);
|
||
DebugUtil.LogError("需要下载正确客户端版本");
|
||
}
|
||
}
|
||
} |