怎样利用优快云论坛公开的API实现自己的论坛工具

本文介绍了优快云论坛提供的API使用方法,包括获取论坛列表、用户信息、发帖及回帖等功能,并提供了积分捐赠、结帖等操作的示例代码。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

csdn论坛公开了一些常用api,不过内部测试阶段,地址是http://forum.youkuaiyun.com/OpenApi/forumapi.asmx还有一个使用的demo,http://forum.youkuaiyun.com/OpenApi/ForumOpenAPIDemo.rar,源码在这里下载demo源码

总体概述:

公开的方法如下:

至于获得帖子和获得帖子列表的方法,虽然没有提供独立的api,但是都可以借助论坛现有的资源,待会会单独讲到

上面的API除了GetForums外,都需要输入一个identity实体,表明你的身份,返回了一个bool型变量,表示操作是否完成,结果会以out变量的形式输出,同时输出的一般还有错误信息Error

identity的参考定义如下

/// <summary>
/// 用户身份信息
/// </summary>
public struct Identity{
/// <summary>
/// 用户名
/// </summary>
public string username;
/// <summary>
/// 密码
/// </summary>
public string password;
}

他包含用于身份验证的用户名和密码,除获得论坛列表以外,其他的操作均要求此参数,调用者可以将用户信息加密存与本地,详细请参考账户管理


而错误信息的参考定义如下

/// <summary>
/// 错误信息
/// </summary>
public struct Error
{
/// <summary>
/// 错误id
/// </summary>
public int errId;

private string _errInfo;
/// <summary>
/// 错误信息
/// </summary>
public string errInfo;

/// <summary>
/// 描述
/// </summary>
public string description;

}

这个实体存放了调用过程中返回的错误,如果返回结果为false,我们就可以查看或者错误信息:

比如下面的积分捐赠的代码段

Identityid = dp.GetDefaultAccount();
Errorerror;

if ( ! openApiService.PointDonate(dp.GetDefaultAccount(),tbUserName.Text,point, " abc " , out error))
ErrorForm.ShowDialog(error);
else
MessageBox.Show(
" 捐赠成功 " );

获得论坛GetForums

GetForums 非常的简单,没有传入参数,方法的返回值是一个Forum实体数组

Forum的参考定义和具体字段含义如下

/// <summary>
/// 论坛信息
/// </summary>
public struct Forum
{
/// <summary>
/// 论坛id
/// </summary>
public GuidforumId;
/// <summary>
/// 父论坛id
/// </summary>
public GuidparentForumId;
/// <summary>
/// 论坛名称
/// </summary>
public string name;
/// <summary>
/// 别名
/// </summary>
public string alias;
/// <summary>
/// 是否技术论坛
/// </summary>
public bool IsTech;
/// <summary>
/// 版主
/// </summary>
public string []morderators;
/// <summary>
/// 积分归属论坛
/// </summary>
public GuidpointBelongsToForumId;

}


获得用户信息GetUserProfile :

方法定义如下:

/// <summary>
/// 获得用户信息
/// </summary>
/// <paramname="identity"> 用户身份信息 </param>
/// <paramname="profile"> 用户信息 </param>
/// <paramname="error"> 错误信息 </param>
/// <paramname="username"> 需要获得用户信息的用户名 </param>
/// <returns> 操作是否成功 </returns>
public bool GetUserProfile(Identityidentity, string username, out UserProfileprofile, out Errorerror)

此方法用于查询某用户的用户信息,包括用户昵称,可用分,用户技术专家分,非技术专家分,以及他在各个论坛的得分和级别(只展示用户在其有得分的论坛信息)

用户信息UserProfile的参考定义和字段含义如下

public struct UserProfile
{
/// <summary>
/// 可用分
/// </summary>
public int point;
/// <summary>
/// 技术专家分
/// </summary>
public int techExpertPoint;
/// <summary>
/// 用户在各个论坛的积分和级别信息
/// </summary>
public List < TopForum > topForums;
/// <summary>
/// 非技术专家分
/// </summary>
public int nonTechExpertPoint;
/// <summary>
/// 昵称
/// </summary>
public string nickName;
/// <summary>
/// 用户名
/// </summary>
public string username;
}

/// <summary>
/// 用户在各个论坛的积分和级别
/// </summary>
public struct TopForum{
/// <summary>
/// 论坛
/// </summary>
public GuidforumId;
/// <summary>
/// 专家分
/// </summary>
public int expertPoint;
/// <summary>
/// 星级
/// </summary>
public string rank;
}

发帖Post :

发帖方法定义如下

/**/ ///<summary>
///发帖
///</summary>
///<paramname="identity">用户身份证</param>
///<paramname="post">帖子</param>
///<paramname="error">错误信息</param>
///<paramname="topicUrl">帖子链接</param>
///<returns>发帖是否成功</returns>

public bool Post(Identityidentity,Postpost, out Errorerror, out string topicUrl)

Post结构参考定义

/// <summary>
/// 帖子
/// </summary>
public struct Post
{
/// <summary>
/// 论坛id(发帖时必须)
/// </summary>
public GuidforumId;
/// <summary>
/// 标题(发帖时必须)
/// </summary>
public string subject;
/// <summary>
/// 帖子内容(发帖时必须)
/// </summary>
public string body;
/// <summary>
/// 标签
/// </summary>
public string tag;
/// <summary>
/// 给分
/// </summary>
public int point;
/// <summary>
/// 是否问专家贴(发帖时必须)
/// </summary>
public bool isAskExpert;
/// <summary>
/// 专家用户名称(若isAskExpert,必须)
/// </summary>
public string expertUserName;
/// <summary>
/// 编辑器类型(发帖时必须),现只支持ubb类型
/// </summary>
public EditorTypeeditor;
/// <summary>
/// 帖子链接
/// </summary>
public string url;

}

回帖Reply :

/**/ ///<summary>
///回复帖子
///</summary>
///<paramname="identity">用户身份证</param>
///<paramname="reply">回复</param>
///<paramname="error">错误信息</param>
///<paramname="replyId">回复id</param>
///<paramname="layer">楼层</param>
///<returns>回复是否成功</returns>

public bool Reply(Identityidentity,Replyreply, out Errorerror, out long replyId, out int layer)

回复实体参考定义如下

/// <summary>
/// 回复
/// </summary>
public struct Reply
{
/// <summary>
/// 论坛id(必须)
/// </summary>
public GuidforumId;
/// <summary>
/// 帖子url(必须)
/// </summary>
public string topicUrl;
/// <summary>
/// 回复内容(必须)
/// </summary>
public string body;
/// <summary>
/// 是否需要ubb(必须)
/// </summary>
public EditorTypeeditor;
}

结帖CheckOutTopic:

/// <summary>
/// 结贴
/// </summary>
/// <paramname="identity"> 用户身份证 </param>
/// <paramname="topicUrl"> 帖子链接 </param>
/// <paramname="forumId"> 论坛id </param>
/// <paramname="replyPoints"> 回复给分列表 </param>
/// <paramname="error"> 错误 </param>
/// <returns> 结贴是否成功 </returns>
public bool CheckOutTopic(Identityidentity, string topicUrl,GuidforumId,List < ReplyPoint > replyPoints, out Errorerror)

List<ReplyPoint> replyPoints为回复id和给分数组

/// <summary>
/// 回帖得分
/// </summary>
public struct ReplyPoint
{
/// <summary>
/// 回复id
/// </summary>
public long replyId;
/// <summary>
/// 得分
/// </summary>
public int point;
}

积分捐赠PointDonate

/// <summary>
/// 可用分捐赠
/// </summary>
/// <paramname="identity"> 用户身份证 </param>
/// <paramname="toUser"> 捐赠对象 </param>
/// <paramname="point"> 捐赠积分 </param>
/// <paramname="reason"> 原因 </param>
/// <paramname="error"> 错误 </param>
/// <returns> 捐赠是否成功 </returns>
public bool PointDonate(Identityidentity, string toUser, int point, string reason, out Errorerror)

获得我的帖子,我参与的帖子,我得分的帖子,别人问我的帖子 GetTopicsOfUser

/// <summary>
/// 获得我发表的帖子,我回复过的帖子,我得分的帖子
/// </summary>
/// <paramname="listType"> 列表类型 </param>
/// <paramname="forumId"> 论坛id </param>
/// <paramname="posts"> 帖子列表 </param>
/// <paramname="error"> 错误信息 </param>
/// <paramname="identity"> 身份信息 </param>
/// <returns> 是否成功 </returns>
[WebMethod]
public bool GetTopicsOfUser(Identityidentity,UserTopicListTypelistType,GuidforumId, out List < Post > posts, out Errorerror)

列表类型定义如下

/// <summary>
/// 用户帖子列表类型
/// </summary>
public enum UserTopicListType
{
/// <summary>
/// 用户的帖子
/// </summary>
TopicOfUser,

/// <summary>
/// 用户回复过的帖子
/// </summary>
TopicUserJoined,

/// <summary>
/// 用户得分的帖子
/// </summary>
TopicUserRewarded,

/// <summary>
/// 所有问专家
/// </summary>
AllAskExpert
}

获得帖子列表

获得帖子列表,包括

待解决 抢分区 零回复 热点区 已解决 精华区

没有提供独立的Webservice,原因是这些帖子列表均提供了Rss,调用者通过Rss获得需要的信息

一个列子列表的rss链接由论坛别名和列表类型两部分组成

比如灌水乐园抢分区的Rss链接为http://forum.youkuaiyun.com/Rss/FreeZone/RobPointList/

其中黄色部分(FreeZone)为论坛别名,红色部分(RobPointList)表明列表类型为抢分区,我们可以通过如下代码简单实现取得rss并转为dataset

public DataTableGetTopicListRss()
{
string url = " http://forum.youkuaiyun.com/Rss/FreeZone/RobPointList/ " ;
HttpWebRequestrequest
= HttpWebRequest.Create(url) as HttpWebRequest;
WebResponseresponse
= request.GetResponse();
DataSetresult
= new DataSet();
StreamrssStream
= response.GetResponseStream();
StreamReadersr
= new StreamReader(rssStream,Utility.GetEncoding());
result.ReadXml(sr);
return result.Tables[ 2 ];
}

获得与解析帖子

公开的API也没专门获得帖子的方法,主要是处于性能的考虑,想要获得帖子,就直接获取帖子html文件,如果需要帖子的信息,比如发帖人,分数,就必须解析帖子文件,文件中提供了一系列标识(csdnid),让解析者可以通过其找到对应的内容,并且在所附demo中,也提供了一个经过改造的解析模块,调用者可以使用这个模块,通过csdnid来找到帖子文件中具体的内容

什么是csdnid?

打开任意一个帖子文件,里面都会看到一些由csdnid标识的元素,这些元素的属性和内容一般都具有特殊的意义,比如帖子源文件中的下面html代码

< meta id ="topicViewUrl" csdnid ="topicViewUrl" content ="http://topic.youkuaiyun.com/u/20080328/15/ce3f9a96-7f91-4dea-83fb-23beffe36cb8.html" >
< meta csdnid ="sectionId" content ="a3049f56-b572-48f5-89be-4797b70d71cd" >

csdnid="topicViewUrl" 的meta元素的content属性,说明了帖子的url,为:http://topic.youkuaiyun.com/u/20080328/15/ce3f9a96-7f91-4dea-83fb-23beffe36cb8.html

而csdnid="sectionId"的meta元素的content属性,说明了帖子的论坛id为:
a3049f56-b572-48f5-89be-4797b70d71cd

而<var csdnid="topicUsername" id="topicUserName">Orange1997</var>中,此元素的innerHTML为发帖用户名

如何解析帖子文件并得到我们想要的信息

解析html文件有很多方法,这里使用使用经过改进的开源html解析其HtmlAgilityPack,Demo中有此模块,

基本使用方法

加载Html文件

下面方法可以把某个html加载进来

HtmlDocument d = new HtmlDocument();
d.Load("C:\test.html");

Load方法还有多个重载,可以从Stream,StreamReader等对象中加载html文档

加载后使用GetElementsbyCsdnId来获得指定csdnid标识的元素,比如

d.GetElementsbyCsdnId("topicBody"),获得所有用csdnid="topicBody"标识的元素

注意这里的返回值是一个元素数组,因为csdnid和id属性不同,是可以重复的;

下面的代码是demo中用于解析帖子文件的方法,详细使用请看demo源码

private InternalTopicParseFile(StreamReaderreader){
InternalTopicpost
= new InternalTopic();
HtmlDocumentd
= new HtmlDocument();
d.Load(reader);
post.body
= ((HtmlNode)d.GetElementsbyCsdnId( " topicBody " )[ 0 ]).InnerHtml;
post.forumId
= new Guid(((HtmlNode)d.GetElementsbyCsdnId( " sectionId " )[ 0 ]).Attributes[ " content " ].Value);
post.subject
= ((HtmlNode)d.GetElementsbyCsdnId( " topicSubject " )[ 0 ]).InnerHtml;
post.point
=
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值