Authored by chenl

Merge branch '5.8.0-0.44.0' of http://git.yoho.cn/mobile/YH_RNComponent into 5.8.0-0.44.0

@@ -24,27 +24,46 @@ export default class Comments extends React.Component { @@ -24,27 +24,46 @@ export default class Comments extends React.Component {
24 } 24 }
25 25
26 render() { 26 render() {
27 - let url = 'http://head.static.yhbimg.com/yhb-head/2015/11/27/10/02497688cb0268347d08ce3df52af8a23a.jpg?imageView/0/w/100/h/100'; 27 + let {resource} = this.props;
  28 + let avator = resource?resource.get('avator'):'';
  29 + let username = resource?resource.get('username'):'';
  30 + let content = resource?resource.get('content'):'';
  31 + let isPraise = resource?resource.get('isPraise'):'N';
  32 + let praiseNum = resource?resource.get('praiseNum'):0;
  33 + let id = resource?resource.get('id'):0;
  34 + let create_time = resource?resource.get('create_time'):'';
  35 +
  36 + let relayTo = resource?resource.get('relayTo'):null;
  37 + let relayToUsername = relayTo?relayTo.get('username'):'';
  38 +
  39 + let thumbsUpIcon = isPraise=='Y' ? require('../../image/sc_icon.png') : require('../../image/wsc_icon.png');
28 40
29 return ( 41 return (
30 <View style={styles.container}> 42 <View style={styles.container}>
31 <View style={styles.rightContainer}> 43 <View style={styles.rightContainer}>
32 - <YH_Image url={url} style={styles.icon}/> 44 + <YH_Image url={avator} style={styles.icon}/>
33 </View> 45 </View>
34 <View style={styles.leftContainer}> 46 <View style={styles.leftContainer}>
35 <View style={styles.headerContainer}> 47 <View style={styles.headerContainer}>
36 - <Text style={styles.name}>Andy</Text>  
37 - <TouchableOpacity onPress={()=>{this.props.onThumbsUp&&this.props.onThumbsUp('点赞')}}> 48 + <Text style={styles.name}>{username}</Text>
  49 + <TouchableOpacity onPress={()=>{
  50 + this.props.onThumbsUp&&this.props.onThumbsUp(id,isPraise=='Y'?'N':'Y')
  51 + }}>
38 <View style={styles.thumbsUp}> 52 <View style={styles.thumbsUp}>
39 - <Image style={styles.thumbsUpIcon} source={require('../../image/sc_icon.png')}/>  
40 - <Text style={styles.thumbsUpNum}>313</Text> 53 + <Image style={styles.thumbsUpIcon} source={thumbsUpIcon}/>
  54 + <Text style={styles.thumbsUpNum}>{praiseNum}</Text>
41 </View> 55 </View>
42 </TouchableOpacity> 56 </TouchableOpacity>
43 - <Text style={styles.time}>4分钟前</Text> 57 + <Text style={styles.time}>{create_time}</Text>
44 </View> 58 </View>
45 <View style={styles.commentView}> 59 <View style={styles.commentView}>
46 - <TouchableOpacity onPress={()=>{this.props.onComment&&this.props.onComment('评论')}}>  
47 - <Text style={styles.commentText}>店铺 样式修改的需求 是谁负责的 @自定义 我把他拉到讨论组里店铺 样式修改的需求 是谁负责的 @自定义 我把他拉到讨论组里店铺 样式修改的需求 是谁负责的 @自定义 我把他拉到讨论组里店铺 样式修改的需求 是谁负责的 @自定义 我把他拉到讨论组里</Text> 60 + <TouchableOpacity onPress={()=>{this.props.onComment&&this.props.onComment(id)}}>
  61 + {relayTo ? <Text style={styles.commentText}>
  62 + 回复
  63 + <Text style={styles.replayName}>{relayToUsername}</Text>
  64 +
  65 + <Text style={styles.commentText}>{content}</Text>
  66 + </Text> : <Text style={styles.commentText}>{content}</Text>}
48 </TouchableOpacity> 67 </TouchableOpacity>
49 </View> 68 </View>
50 <View style={styles.line}/> 69 <View style={styles.line}/>
@@ -113,6 +132,7 @@ let styles = StyleSheet.create({ @@ -113,6 +132,7 @@ let styles = StyleSheet.create({
113 backgroundColor: 'white', 132 backgroundColor: 'white',
114 fontSize: 12, 133 fontSize: 12,
115 color: 'gray', 134 color: 'gray',
  135 + width: 25,
116 }, 136 },
117 time: { 137 time: {
118 position: 'absolute', 138 position: 'absolute',
@@ -131,6 +151,11 @@ let styles = StyleSheet.create({ @@ -131,6 +151,11 @@ let styles = StyleSheet.create({
131 textAlign: 'left', 151 textAlign: 'left',
132 backgroundColor: 'white', 152 backgroundColor: 'white',
133 fontSize: 15, 153 fontSize: 15,
  154 + },
  155 + replayName: {
  156 + textAlign: 'left',
  157 + backgroundColor: 'white',
  158 + fontSize: 15,
134 fontWeight: 'bold', 159 fontWeight: 'bold',
135 }, 160 },
136 line: { 161 line: {
@@ -24,20 +24,33 @@ export default class CommentsTitle extends React.Component { @@ -24,20 +24,33 @@ export default class CommentsTitle extends React.Component {
24 } 24 }
25 25
26 render() { 26 render() {
27 - //let newSrc = getSlicedUrl(item.src, width, height, 2);  
28 - let url = 'http://head.static.yhbimg.com/yhb-head/2015/11/27/10/02497688cb0268347d08ce3df52af8a23a.jpg?imageView/0/w/100/h/100'; 27 + let {resource,total} = this.props;
  28 + let data = resource?resource.toJS():null;
  29 + let browseNum = data.browseNum?data.browseNum:0;
  30 + let id = data.id?data.id:0;
  31 + let isFavor = data.isFavor?data.isFavor:'N';
  32 + let isPraise = data.isPraise?data.isPraise:'N';
  33 + let praiseHeadIco = data.praiseHeadIco?data.praiseHeadIco:[];
  34 + let praiseNum = data.praiseNum?data.praiseNum:0;
  35 + let praiseText = praiseNum + '人点赞';
  36 + let browseNumText = browseNum + '人看过';
  37 + let title = '评论'+total;
  38 + let url1 = praiseHeadIco.length>0? praiseHeadIco[0]:'';
  39 + let url2 = praiseHeadIco.length>1? praiseHeadIco[1]:'';
  40 + let url3 = praiseHeadIco.length>2? praiseHeadIco[2]:'';
  41 +
29 return ( 42 return (
30 <View style={styles.container}> 43 <View style={styles.container}>
31 <View style={styles.contentContainer}> 44 <View style={styles.contentContainer}>
32 - <YH_Image url={url} style={styles.icon3}/>  
33 - <YH_Image url={url} style={styles.icon2}/>  
34 - <YH_Image url={url} style={styles.icon1}/>  
35 - <Text style={styles.rightText}>210人点赞</Text>  
36 - <Text style={styles.leftText}>9233人看过</Text> 45 + <YH_Image url={url1} style={styles.icon3}/>
  46 + <YH_Image url={url2} style={styles.icon2}/>
  47 + <YH_Image url={url3} style={styles.icon1}/>
  48 + <Text style={styles.rightText}>{praiseText}</Text>
  49 + <Text style={styles.leftText}>{browseNumText}</Text>
37 </View> 50 </View>
38 <View style={{width: width,height: 1,backgroundColor: '#e5e5e5',}}/> 51 <View style={{width: width,height: 1,backgroundColor: '#e5e5e5',}}/>
39 <View style={styles.commentTitle}> 52 <View style={styles.commentTitle}>
40 - <Text style={styles.commentTitleText}>评论2</Text> 53 + <Text style={styles.commentTitleText}>{title}</Text>
41 </View> 54 </View>
42 </View> 55 </View>
43 ); 56 );
@@ -44,7 +44,6 @@ export default class Detail extends Component { @@ -44,7 +44,6 @@ export default class Detail extends Component {
44 this.renderRow = this.renderRow.bind(this); 44 this.renderRow = this.renderRow.bind(this);
45 this.renderHeader = this.renderHeader.bind(this); 45 this.renderHeader = this.renderHeader.bind(this);
46 this.scrollTo = this.scrollTo.bind(this); 46 this.scrollTo = this.scrollTo.bind(this);
47 - this._onThumbsUp = this._onThumbsUp.bind(this);  
48 this._onComment = this._onComment.bind(this); 47 this._onComment = this._onComment.bind(this);
49 this._onSubmitEditing = this._onSubmitEditing.bind(this); 48 this._onSubmitEditing = this._onSubmitEditing.bind(this);
50 this.listView = null; 49 this.listView = null;
@@ -54,6 +53,7 @@ export default class Detail extends Component { @@ -54,6 +53,7 @@ export default class Detail extends Component {
54 }); 53 });
55 this.state = { 54 this.state = {
56 viewMarginTop : new Animated.Value(0), 55 viewMarginTop : new Animated.Value(0),
  56 + replyTo: 0,
57 }; 57 };
58 } 58 }
59 59
@@ -106,16 +106,20 @@ export default class Detail extends Component { @@ -106,16 +106,20 @@ export default class Detail extends Component {
106 } 106 }
107 107
108 _onSubmitEditing(event){ 108 _onSubmitEditing(event){
109 - console.log(event.nativeEvent.text);  
110 - this.refs.textInput.clear();  
111 - } 109 + let content = event.nativeEvent.text;
  110 + let replyTos = this.state.replyTo;
112 111
113 - _onThumbsUp(s){  
114 - console.log(s); 112 + if (this.state.replyTo == 0) {
  113 + replyTos = '';
  114 + }
  115 + this.props.onSubmitForComment && this.props.onSubmitForComment(content,replyTos);
  116 + this.refs.textInput.clear();
  117 + this.setState({replyTo: 0});
115 } 118 }
116 119
117 - _onComment(s){  
118 - console.log(s); 120 + _onComment(id){
  121 + this.setState({replyTo: id});
  122 + this.refs.textInput && this.refs.textInput.focus();
119 } 123 }
120 124
121 renderHeader() { 125 renderHeader() {
@@ -189,12 +193,15 @@ export default class Detail extends Component { @@ -189,12 +193,15 @@ export default class Detail extends Component {
189 <WeChatPublic resource={rowData} onPressWeixin={this.props.onPressWeixin}/> 193 <WeChatPublic resource={rowData} onPressWeixin={this.props.onPressWeixin}/>
190 ); 194 );
191 } else if (sectionID == 'commentsTitle'){ 195 } else if (sectionID == 'commentsTitle'){
  196 + let {resource} = this.props;
  197 + let {commentsList} = resource;
  198 + let total = commentsList?commentsList.get('total'):0;
192 return ( 199 return (
193 - <CommentsTitle resource={rowData} /> 200 + <CommentsTitle resource={rowData} total={total}/>
194 ); 201 );
195 }else if (sectionID == 'comments'){ 202 }else if (sectionID == 'comments'){
196 return ( 203 return (
197 - <Comments resource={rowData} onThumbsUp={this._onThumbsUp} onComment={this._onComment}/> 204 + <Comments resource={rowData} onThumbsUp={this.props.addPraiseForComments} onComment={this._onComment}/>
198 ); 205 );
199 }else if (sectionID == 'space'){ 206 }else if (sectionID == 'space'){
200 return ( 207 return (
@@ -217,22 +224,31 @@ export default class Detail extends Component { @@ -217,22 +224,31 @@ export default class Detail extends Component {
217 weixin, 224 weixin,
218 goods_group_Filter, 225 goods_group_Filter,
219 wechat, 226 wechat,
  227 + commentsList,
  228 + addComment,
  229 + addPraiseInfo,
220 } = resource; 230 } = resource;
221 231
222 - let list = content?content.get('data'):[]; 232 + let list = content?content.get('data'):null;
  233 + let comments = commentsList?commentsList.get('data'):null;
  234 +
223 let dataSource = { 235 let dataSource = {
224 - detailList: list.size?list.toArray():[], 236 + detailList: list&&list.size>0?list.toArray():[],
225 weixin: [weixin], 237 weixin: [weixin],
226 detailBrand: [brand], 238 detailBrand: [brand],
227 detailOtherArticle: [otherArticle], 239 detailOtherArticle: [otherArticle],
228 tags:[article], 240 tags:[article],
229 weChatPublic: [wechat], 241 weChatPublic: [wechat],
230 - commentsTitle: ['1'],  
231 - comments: ['1','2'], 242 + commentsTitle: [addPraiseInfo],
  243 + comments: comments&&comments.size>0?comments.toArray():[],
232 space: ['1'], 244 space: ['1'],
233 }; 245 };
234 246
235 let isFetching = content.isFetching || article.isFetching || author.isFetching; 247 let isFetching = content.isFetching || article.isFetching || author.isFetching;
  248 + let isFavor = addPraiseInfo.get('isFavor')?addPraiseInfo.get('isFavor'):'N';
  249 + let isPraise = addPraiseInfo.get('isPraise')?addPraiseInfo.get('isPraise'):'N';
  250 + let isFavorIcon = isFavor=='Y' ? require('../../image/sc_icon.png') : require('../../image/wsc_icon.png');
  251 + let isPraiseIcon = isPraise=='Y' ? require('../../image/sc_icon.png') : require('../../image/wsc_icon.png');
236 252
237 return ( 253 return (
238 <View style={styles.container}> 254 <View style={styles.container}>
@@ -258,11 +274,13 @@ export default class Detail extends Component { @@ -258,11 +274,13 @@ export default class Detail extends Component {
258 onSubmitEditing = {this._onSubmitEditing} 274 onSubmitEditing = {this._onSubmitEditing}
259 clearButtonMode = 'while-editing' 275 clearButtonMode = 'while-editing'
260 ref = 'textInput'/> 276 ref = 'textInput'/>
261 - <TouchableOpacity onPress={()=>{this.props.onPressConcerns&&this.props.onPressConcerns('关注')}}>  
262 - <Image style={styles.favIcon} source={require('../../image/sc_icon.png')}/> 277 + <TouchableOpacity onPress={()=>{
  278 + this.props.onPressConcerns&&this.props.onPressConcerns(isFavor)}
  279 + }>
  280 + <Image style={styles.favIcon} source={isFavorIcon}/>
263 </TouchableOpacity> 281 </TouchableOpacity>
264 - <TouchableOpacity onPress={()=>{this._onThumbsUp&&this._onThumbsUp('点赞')}}>  
265 - <Image style={styles.thumbsUpIcon} source={require('../../image/sc_icon.png')}/> 282 + <TouchableOpacity onPress={()=>{this.props.addPraiseForArtivle&&this.props.addPraiseForArtivle(isPraise)}}>
  283 + <Image style={styles.thumbsUpIcon} source={isPraiseIcon}/>
266 </TouchableOpacity> 284 </TouchableOpacity>
267 </View> 285 </View>
268 </Animated.View> 286 </Animated.View>
@@ -53,4 +53,43 @@ export default keyMirror({ @@ -53,4 +53,43 @@ export default keyMirror({
53 GET_WECHAT_ATTEN_FAILURE: null, 53 GET_WECHAT_ATTEN_FAILURE: null,
54 54
55 LIKE_ARTICLE: null, 55 LIKE_ARTICLE: null,
  56 +
  57 + //获取资讯评论列表
  58 + GET_COMMENTS_LIST_REQUEST: null,
  59 + GET_COMMENTS_LIST_SUCCESS: null,
  60 + GET_COMMENTS_LIST_FAILURE: null,
  61 +
  62 + //资讯添加评论
  63 + ADD_COMMENTS_FOR_ARTIVLE_REQUEST: null,
  64 + ADD_COMMENTS_FOR_ARTIVLE_SUCCESS: null,
  65 + ADD_COMMENTS_FOR_ARTIVLE_FAILURE: null,
  66 +
  67 + //资讯内容点赞
  68 + ADD_PRAISE_FOR_COMMENTS_REQUEST: null,
  69 + ADD_PRAISE_FOR_COMMENTS_SUCCESS: null,
  70 + ADD_PRAISE_FOR_COMMENTS_FAILURE: null,
  71 +
  72 + //文章点赞Info
  73 + GET_PRAISE_FOR_ARTIVLE_REQUEST: null,
  74 + GET_PRAISE_FOR_ARTIVLE_SUCCESS: null,
  75 + GET_PRAISE_FOR_ARTIVLE_FAILURE: null,
  76 +
  77 + SET_PRAISE_FOR_COMMENTS: null,
  78 +
  79 + //点赞文章
  80 + PRAISE_FOR_ARTIVLE_REQUEST: null,
  81 + PRAISE_FOR_ARTIVLE_SUCCESS: null,
  82 + PRAISE_FOR_ARTIVLE_FAILURE: null,
  83 + //取消点赞文章
  84 + CANCEL_PRAISE_FOR_ARTIVLE_REQUEST: null,
  85 + CANCEL_PRAISE_FOR_ARTIVLE_SUCCESS: null,
  86 + CANCEL_PRAISE_FOR_ARTIVLE_FAILURE: null,
  87 + //收藏
  88 + ADD_FAVORITE_REQUEST: null,
  89 + ADD_FAVORITE_SUCCESS: null,
  90 + ADD_FAVORITE_FAILURE: null,
  91 + //取消收藏
  92 + CANCEL_FAVORITE_REQUEST: null,
  93 + CANCEL_FAVORITE_SUCCESS: null,
  94 + CANCEL_FAVORITE_FAILURE: null,
56 }); 95 });
@@ -60,6 +60,10 @@ class DetailContainer extends Component { @@ -60,6 +60,10 @@ class DetailContainer extends Component {
60 this._onPressShopCar = this._onPressShopCar.bind(this); 60 this._onPressShopCar = this._onPressShopCar.bind(this);
61 this._onPressTagProduct = this._onPressTagProduct.bind(this); 61 this._onPressTagProduct = this._onPressTagProduct.bind(this);
62 this._onPressConcerns = this._onPressConcerns.bind(this); 62 this._onPressConcerns = this._onPressConcerns.bind(this);
  63 + this._onSubmitForComment = this._onSubmitForComment.bind(this);
  64 + this._addPraiseForArtivle = this._addPraiseForArtivle.bind(this);
  65 + this._addPraiseForComments = this._addPraiseForComments.bind(this);
  66 +
63 } 67 }
64 68
65 componentDidMount() { 69 componentDidMount() {
@@ -68,14 +72,37 @@ class DetailContainer extends Component { @@ -68,14 +72,37 @@ class DetailContainer extends Component {
68 this.props.actions.getBrand(); 72 this.props.actions.getBrand();
69 this.props.actions.getWeixinPublic(); 73 this.props.actions.getWeixinPublic();
70 this.props.actions.getWeChatAtten(); 74 this.props.actions.getWeChatAtten();
  75 + this.props.actions.getCommentsList();
  76 + this.props.actions.getPraiseForArtivle();
71 } 77 }
72 78
73 componentWillUnmount() { 79 componentWillUnmount() {
74 80
75 } 81 }
76 82
77 - _onPressConcerns(e){  
78 - console.log(e); 83 + _onSubmitForComment(content,replyTo){
  84 + this.props.actions.addCommentsForArtivle(content,replyTo);
  85 + }
  86 +
  87 + _onPressConcerns(isFav){
  88 + if (isFav == 'N') {
  89 + this.props.actions.addFavorite();
  90 + }else {
  91 + this.props.actions.cancelFavorite();
  92 + }
  93 + }
  94 +
  95 + _addPraiseForArtivle(isPraise){
  96 + if (isPraise == 'N') {
  97 + this.props.actions.praiseForArtivle();
  98 + }else {
  99 + this.props.actions.cancelPraiseForArtivle();
  100 + }
  101 + }
  102 +
  103 + _addPraiseForComments(comment_id,praise){
  104 + this.props.actions.setPraiseForComments(comment_id,praise);
  105 + this.props.actions.addPraiseForComments(comment_id,praise);
79 } 106 }
80 107
81 _onPressFilter(value) { 108 _onPressFilter(value) {
@@ -230,6 +257,9 @@ class DetailContainer extends Component { @@ -230,6 +257,9 @@ class DetailContainer extends Component {
230 onPressShopCar={this._onPressShopCar} 257 onPressShopCar={this._onPressShopCar}
231 onPressTagProduct={this._onPressTagProduct} 258 onPressTagProduct={this._onPressTagProduct}
232 onPressConcerns={this._onPressConcerns} 259 onPressConcerns={this._onPressConcerns}
  260 + onSubmitForComment={this._onSubmitForComment}
  261 + addPraiseForArtivle={this._addPraiseForArtivle}
  262 + addPraiseForComments={this._addPraiseForComments}
233 /> 263 />
234 </View> 264 </View>
235 ); 265 );
@@ -43,6 +43,44 @@ const { @@ -43,6 +43,44 @@ const {
43 SET_GOOESGROUP_FILTER, 43 SET_GOOESGROUP_FILTER,
44 SET_GOOESGROUP_Y, 44 SET_GOOESGROUP_Y,
45 45
  46 + //获取资讯评论列表
  47 + GET_COMMENTS_LIST_REQUEST,
  48 + GET_COMMENTS_LIST_SUCCESS,
  49 + GET_COMMENTS_LIST_FAILURE,
  50 +
  51 + //资讯添加评论
  52 + ADD_COMMENTS_FOR_ARTIVLE_REQUEST,
  53 + ADD_COMMENTS_FOR_ARTIVLE_SUCCESS,
  54 + ADD_COMMENTS_FOR_ARTIVLE_FAILURE,
  55 +
  56 + //资讯内容点赞
  57 + ADD_PRAISE_FOR_COMMENTS_REQUEST,
  58 + ADD_PRAISE_FOR_COMMENTS_SUCCESS,
  59 + ADD_PRAISE_FOR_COMMENTS_FAILURE,
  60 +
  61 + //文章点赞Info
  62 + GET_PRAISE_FOR_ARTIVLE_REQUEST,
  63 + GET_PRAISE_FOR_ARTIVLE_SUCCESS,
  64 + GET_PRAISE_FOR_ARTIVLE_FAILURE,
  65 +
  66 + SET_PRAISE_FOR_COMMENTS,
  67 +
  68 + //点赞文章
  69 + PRAISE_FOR_ARTIVLE_REQUEST,
  70 + PRAISE_FOR_ARTIVLE_SUCCESS,
  71 + PRAISE_FOR_ARTIVLE_FAILURE,
  72 + //取消点赞文章
  73 + CANCEL_PRAISE_FOR_ARTIVLE_REQUEST,
  74 + CANCEL_PRAISE_FOR_ARTIVLE_SUCCESS,
  75 + CANCEL_PRAISE_FOR_ARTIVLE_FAILURE,
  76 + //收藏
  77 + ADD_FAVORITE_REQUEST,
  78 + ADD_FAVORITE_SUCCESS,
  79 + ADD_FAVORITE_FAILURE,
  80 + //取消收藏
  81 + CANCEL_FAVORITE_REQUEST,
  82 + CANCEL_FAVORITE_SUCCESS,
  83 + CANCEL_FAVORITE_FAILURE,
46 } = require('../../constants/actionTypes').default; 84 } = require('../../constants/actionTypes').default;
47 85
48 export function setArticleId(id) { 86 export function setArticleId(id) {
@@ -674,3 +712,419 @@ function parseWeChatData(json) { @@ -674,3 +712,419 @@ function parseWeChatData(json) {
674 wechatCopy, 712 wechatCopy,
675 } 713 }
676 } 714 }
  715 +
  716 +function getCommentsListRequest() {
  717 + return {
  718 + type: GET_COMMENTS_LIST_REQUEST,
  719 + };
  720 +}
  721 +
  722 +function getCommentsListSuccess(json) {
  723 + return {
  724 + type: GET_COMMENTS_LIST_SUCCESS,
  725 + payload: json
  726 + };
  727 +}
  728 +
  729 +function getCommentsListFailure(error) {
  730 + return {
  731 + type: GET_COMMENTS_LIST_FAILURE,
  732 + payload: error
  733 + };
  734 +}
  735 +
  736 +export function getCommentsList() {
  737 + return (dispatch, getState) => {
  738 + let {app, detail} = getState();
  739 + let {articleId, article,commentsList} = detail;
  740 + let page = commentsList.page;
  741 + let list = commentsList.data;
  742 + let limit = commentsList.limit;
  743 + let total_page = commentsList.total_page;
  744 + if (list && list.length > 0 && total_page <= page) {
  745 + return;
  746 + }
  747 +
  748 + dispatch(getCommentsListRequest());
  749 + return new DetailService(app.serviceHost).getCommentsList(articleId,page,limit)
  750 + .then(json => {
  751 + let param = parseCommentsData(json)
  752 + dispatch(getCommentsListSuccess(param));
  753 + })
  754 + .catch(error => {
  755 + dispatch(getCommentsListFailure(error));
  756 + });
  757 + };
  758 +}
  759 +
  760 +function parseCommentsData(json) {
  761 + let data = [];
  762 + let page = 1;
  763 + let total = 0;
  764 + let total_page = 0;
  765 +
  766 + if (json) {
  767 + data = json.list;
  768 + page = json.page;
  769 + total = json.total;
  770 + total_page = json.total_page;
  771 + }
  772 + return {
  773 + data,
  774 + page,
  775 + total,
  776 + total_page,
  777 + }
  778 +}
  779 +
  780 +
  781 +function addCommentsForArtivleRequest() {
  782 + return {
  783 + type: ADD_COMMENTS_FOR_ARTIVLE_REQUEST,
  784 + };
  785 +}
  786 +
  787 +function addCommentsForArtivleSuccess(json) {
  788 + return {
  789 + type: ADD_COMMENTS_FOR_ARTIVLE_SUCCESS,
  790 + payload: json
  791 + };
  792 +}
  793 +
  794 +function addCommentsForArtivleFailure(error) {
  795 + return {
  796 + type: ADD_COMMENTS_FOR_ARTIVLE_FAILURE,
  797 + payload: error
  798 + };
  799 +}
  800 +
  801 +export function addCommentsForArtivle(content,replyTo) {
  802 + return (dispatch, getState) => {
  803 + let {app, detail} = getState();
  804 + let {articleId, article} = detail;
  805 + let article_id = articleId;
  806 +
  807 + let fetchInfo = (article_id,uid) => {
  808 + dispatch(addCommentsForArtivleRequest());
  809 + return new DetailService(app.serviceHost).addCommentsForArtivle(article_id,uid,content,replyTo)
  810 + .then(json => {
  811 + dispatch(addCommentsForArtivleSuccess(json));
  812 + })
  813 + .catch(error => {
  814 + dispatch(addCommentsForArtivleFailure(error));
  815 + });
  816 + }
  817 +
  818 + ReactNative.NativeModules.YH_CommonHelper.uid()
  819 + .then(uid => {
  820 + fetchInfo(article_id,uid);
  821 + })
  822 + .catch(error => {
  823 + ReactNative.NativeModules.YH_CommonHelper.login()
  824 + .then(uid => {
  825 + fetchInfo(article_id,uid);
  826 + })
  827 + .catch(error => {
  828 +
  829 + });
  830 + });
  831 + };
  832 +}
  833 +
  834 +function setPraiseForCommentsReq(json) {
  835 + return {
  836 + type: SET_PRAISE_FOR_COMMENTS,
  837 + payload: json
  838 + };
  839 +}
  840 +
  841 +export function setPraiseForComments(comment_id,praise) {
  842 + return (dispatch, getState) => {
  843 + let {app, detail} = getState();
  844 + let {commentsList} = detail;
  845 + let comments = commentsList?commentsList.toJS():null;
  846 + let list = comments?comments.data:null;
  847 + list && list.map((item, i) => {
  848 + if (comment_id == item.id) {
  849 + item.isPraise = praise;
  850 + let num = item.praiseNum?item.praiseNum:0;
  851 + if (praise === 'Y') {
  852 + item.praiseNum = num + 1;
  853 + }else {
  854 + item.praiseNum = num - 1 <= 0 ? 0 : num - 1;
  855 + }
  856 + }
  857 + });
  858 + dispatch(setPraiseForCommentsReq(list));
  859 + };
  860 +}
  861 +
  862 +function addPraiseForCommentsRequest() {
  863 + return {
  864 + type: ADD_PRAISE_FOR_COMMENTS_REQUEST,
  865 + };
  866 +}
  867 +
  868 +function addPraiseForCommentsSuccess(json) {
  869 + return {
  870 + type: ADD_PRAISE_FOR_COMMENTS_SUCCESS,
  871 + payload: json
  872 + };
  873 +}
  874 +
  875 +function addPraiseForCommentsFailure(error) {
  876 + return {
  877 + type: ADD_PRAISE_FOR_COMMENTS_FAILURE,
  878 + payload: error
  879 + };
  880 +}
  881 +
  882 +export function addPraiseForComments(comment_id,praise) {
  883 + return (dispatch, getState) => {
  884 + let {app, detail} = getState();
  885 + let {articleId, article} = detail;
  886 + let article_id = articleId;
  887 +
  888 + dispatch(addPraiseForCommentsRequest());
  889 + return new DetailService(app.serviceHost).addPraiseForComments(comment_id,praise,article_id)
  890 + .then(json => {
  891 + dispatch(addPraiseForCommentsSuccess(json));
  892 + })
  893 + .catch(error => {
  894 + dispatch(addPraiseForCommentsFailure(error));
  895 + });
  896 + };
  897 +}
  898 +
  899 +function getPraiseForArtivleRequest() {
  900 + return {
  901 + type: GET_PRAISE_FOR_ARTIVLE_REQUEST,
  902 + };
  903 +}
  904 +
  905 +function getPraiseForArtivleSuccess(json) {
  906 + return {
  907 + type: GET_PRAISE_FOR_ARTIVLE_SUCCESS,
  908 + payload: json
  909 + };
  910 +}
  911 +
  912 +function getPraiseForArtivleFailure(error) {
  913 + return {
  914 + type: GET_PRAISE_FOR_ARTIVLE_FAILURE,
  915 + payload: error
  916 + };
  917 +}
  918 +
  919 +export function getPraiseForArtivle() {
  920 + return (dispatch, getState) => {
  921 + let {app, detail} = getState();
  922 + let {articleId, article} = detail;
  923 + let id = articleId;
  924 +
  925 + let fetchInfo = (id,uid) => {
  926 + dispatch(getPraiseForArtivleRequest());
  927 + return new DetailService(app.serviceHost).getPraiseForArtivle(uid,id)
  928 + .then(json => {
  929 + dispatch(getPraiseForArtivleSuccess(json));
  930 + })
  931 + .catch(error => {
  932 + dispatch(getPraiseForArtivleFailure(error));
  933 + });
  934 + }
  935 +
  936 + ReactNative.NativeModules.YH_CommonHelper.uid()
  937 + .then(uid => {
  938 + fetchInfo(id,uid);
  939 + })
  940 + .catch(error => {
  941 + ReactNative.NativeModules.YH_CommonHelper.login()
  942 + .then(uid => {
  943 + fetchInfo(id,uid);
  944 + })
  945 + .catch(error => {
  946 +
  947 + });
  948 + });
  949 + };
  950 +}
  951 +
  952 +function praiseForArtivleRequest() {
  953 + return {
  954 + type: PRAISE_FOR_ARTIVLE_REQUEST,
  955 + };
  956 +}
  957 +
  958 +function praiseForArtivleSuccess(json) {
  959 + return {
  960 + type: PRAISE_FOR_ARTIVLE_SUCCESS,
  961 + payload: json
  962 + };
  963 +}
  964 +
  965 +function praiseForArtivleFailure(error) {
  966 + return {
  967 + type: PRAISE_FOR_ARTIVLE_FAILURE,
  968 + payload: error
  969 + };
  970 +}
  971 +
  972 +export function praiseForArtivle() {
  973 + return (dispatch, getState) => {
  974 + let {app, detail} = getState();
  975 + let {articleId, article} = detail;
  976 + let article_id = articleId;
  977 +
  978 + dispatch(praiseForArtivleRequest());
  979 + return new DetailService(app.serviceHost).praiseForArtivle(article_id)
  980 + .then(json => {
  981 + dispatch(praiseForArtivleSuccess(json));
  982 + })
  983 + .catch(error => {
  984 + dispatch(praiseForArtivleFailure(error));
  985 + });
  986 + };
  987 +}
  988 +
  989 +function cancelPraiseForArtivleRequest() {
  990 + return {
  991 + type: CANCEL_PRAISE_FOR_ARTIVLE_REQUEST,
  992 + };
  993 +}
  994 +
  995 +function cancelPraiseForArtivleSuccess(json) {
  996 + return {
  997 + type: CANCEL_PRAISE_FOR_ARTIVLE_SUCCESS,
  998 + payload: json
  999 + };
  1000 +}
  1001 +
  1002 +function cancelPraiseForArtivleFailure(error) {
  1003 + return {
  1004 + type: CANCEL_PRAISE_FOR_ARTIVLE_FAILURE,
  1005 + payload: error
  1006 + };
  1007 +}
  1008 +
  1009 +export function cancelPraiseForArtivle() {
  1010 + return (dispatch, getState) => {
  1011 + let {app, detail} = getState();
  1012 + let {articleId, article} = detail;
  1013 + let article_id = articleId;
  1014 +
  1015 + dispatch(cancelPraiseForArtivleRequest());
  1016 + return new DetailService(app.serviceHost).cancelPraiseForArtivle(article_id)
  1017 + .then(json => {
  1018 + dispatch(cancelPraiseForArtivleSuccess(json));
  1019 + })
  1020 + .catch(error => {
  1021 + dispatch(cancelPraiseForArtivleFailure(error));
  1022 + });
  1023 + };
  1024 +}
  1025 +
  1026 +function addFavoriteRequest() {
  1027 + return {
  1028 + type: ADD_FAVORITE_REQUEST,
  1029 + };
  1030 +}
  1031 +
  1032 +function addFavoriteSuccess(json) {
  1033 + return {
  1034 + type: ADD_FAVORITE_SUCCESS,
  1035 + payload: json
  1036 + };
  1037 +}
  1038 +
  1039 +function addFavoriteFailure(error) {
  1040 + return {
  1041 + type: ADD_FAVORITE_FAILURE,
  1042 + payload: error
  1043 + };
  1044 +}
  1045 +
  1046 +export function addFavorite() {
  1047 + return (dispatch, getState) => {
  1048 + let {app, detail} = getState();
  1049 + let {articleId, article} = detail;
  1050 + let article_id = articleId;
  1051 +
  1052 + let fetchInfo = (article_id,uid) => {
  1053 + dispatch(addFavoriteRequest());
  1054 + return new DetailService(app.serviceHost).addFavorite(uid,article_id)
  1055 + .then(json => {
  1056 + dispatch(addFavoriteSuccess(json));
  1057 + })
  1058 + .catch(error => {
  1059 + dispatch(addFavoriteFailure(error));
  1060 + });
  1061 + }
  1062 +
  1063 + ReactNative.NativeModules.YH_CommonHelper.uid()
  1064 + .then(uid => {
  1065 + fetchInfo(article_id,uid);
  1066 + })
  1067 + .catch(error => {
  1068 + ReactNative.NativeModules.YH_CommonHelper.login()
  1069 + .then(uid => {
  1070 + fetchInfo(article_id,uid);
  1071 + })
  1072 + .catch(error => {
  1073 +
  1074 + });
  1075 + });
  1076 + };
  1077 +}
  1078 +
  1079 +function cancelFavoriteRequest() {
  1080 + return {
  1081 + type: CANCEL_FAVORITE_REQUEST,
  1082 + };
  1083 +}
  1084 +
  1085 +function cancelFavoriteSuccess(json) {
  1086 + return {
  1087 + type: CANCEL_FAVORITE_SUCCESS,
  1088 + payload: json
  1089 + };
  1090 +}
  1091 +
  1092 +function cancelFavoriteFailure(error) {
  1093 + return {
  1094 + type: CANCEL_FAVORITE_FAILURE,
  1095 + payload: error
  1096 + };
  1097 +}
  1098 +
  1099 +export function cancelFavorite() {
  1100 + return (dispatch, getState) => {
  1101 + let {app, detail} = getState();
  1102 + let {articleId, article} = detail;
  1103 + let article_id = articleId;
  1104 +
  1105 + let fetchInfo = (article_id,uid) => {
  1106 + dispatch(cancelFavoriteRequest());
  1107 + return new DetailService(app.serviceHost).cancelFavorite(uid,article_id)
  1108 + .then(json => {
  1109 + dispatch(cancelFavoriteSuccess(json));
  1110 + })
  1111 + .catch(error => {
  1112 + dispatch(cancelFavoriteFailure(error));
  1113 + });
  1114 + }
  1115 +
  1116 + ReactNative.NativeModules.YH_CommonHelper.uid()
  1117 + .then(uid => {
  1118 + fetchInfo(article_id,uid);
  1119 + })
  1120 + .catch(error => {
  1121 + ReactNative.NativeModules.YH_CommonHelper.login()
  1122 + .then(uid => {
  1123 + fetchInfo(article_id,uid);
  1124 + })
  1125 + .catch(error => {
  1126 +
  1127 + });
  1128 + });
  1129 + };
  1130 +}
@@ -43,6 +43,31 @@ let InitialState = Record({ @@ -43,6 +43,31 @@ let InitialState = Record({
43 })), 43 })),
44 goods_group_Filter: 0, 44 goods_group_Filter: 0,
45 goods_group_y: 0, 45 goods_group_y: 0,
  46 + commentsList: new (Record({
  47 + isFetching: false,
  48 + error: null,
  49 + data: List(),
  50 + page: 1,
  51 + total: 0,
  52 + total_page: 0,
  53 + limit: 10,
  54 + })),
  55 + addComment: new (Record({
  56 + isFetching: false,
  57 + error: null,
  58 + data: List(),
  59 + message: '',
  60 + })),
  61 + addPraiseInfo: new (Record({
  62 + isFetching: false,
  63 + error: null,
  64 + browseNum: 0,
  65 + id: 0,
  66 + isFavor: 'N',
  67 + isPraise: 'N',
  68 + praiseHeadIco: List(),
  69 + praiseNum: 0,
  70 + })),
46 }); 71 });
47 72
48 export default InitialState; 73 export default InitialState;
@@ -39,6 +39,46 @@ const { @@ -39,6 +39,46 @@ const {
39 SET_GOOESGROUP_FILTER, 39 SET_GOOESGROUP_FILTER,
40 SET_GOOESGROUP_Y, 40 SET_GOOESGROUP_Y,
41 41
  42 +
  43 + //获取资讯评论列表
  44 + GET_COMMENTS_LIST_REQUEST,
  45 + GET_COMMENTS_LIST_SUCCESS,
  46 + GET_COMMENTS_LIST_FAILURE,
  47 +
  48 + //资讯添加评论
  49 + ADD_COMMENTS_FOR_ARTIVLE_REQUEST,
  50 + ADD_COMMENTS_FOR_ARTIVLE_SUCCESS,
  51 + ADD_COMMENTS_FOR_ARTIVLE_FAILURE,
  52 +
  53 + //资讯内容点赞
  54 + ADD_PRAISE_FOR_COMMENTS_REQUEST,
  55 + ADD_PRAISE_FOR_COMMENTS_SUCCESS,
  56 + ADD_PRAISE_FOR_COMMENTS_FAILURE,
  57 +
  58 + //文章点赞Info
  59 + GET_PRAISE_FOR_ARTIVLE_REQUEST,
  60 + GET_PRAISE_FOR_ARTIVLE_SUCCESS,
  61 + GET_PRAISE_FOR_ARTIVLE_FAILURE,
  62 +
  63 + SET_PRAISE_FOR_COMMENTS,
  64 +
  65 + //点赞文章
  66 + PRAISE_FOR_ARTIVLE_REQUEST,
  67 + PRAISE_FOR_ARTIVLE_SUCCESS,
  68 + PRAISE_FOR_ARTIVLE_FAILURE,
  69 + //取消点赞文章
  70 + CANCEL_PRAISE_FOR_ARTIVLE_REQUEST,
  71 + CANCEL_PRAISE_FOR_ARTIVLE_SUCCESS,
  72 + CANCEL_PRAISE_FOR_ARTIVLE_FAILURE,
  73 + //收藏
  74 + ADD_FAVORITE_REQUEST,
  75 + ADD_FAVORITE_SUCCESS,
  76 + ADD_FAVORITE_FAILURE,
  77 + //取消收藏
  78 + CANCEL_FAVORITE_REQUEST,
  79 + CANCEL_FAVORITE_SUCCESS,
  80 + CANCEL_FAVORITE_FAILURE,
  81 +
42 } = require('../../constants/actionTypes').default; 82 } = require('../../constants/actionTypes').default;
43 83
44 const initialState = new InitialState; 84 const initialState = new InitialState;
@@ -175,6 +215,97 @@ export default function detailReducer(state=initialState, action) { @@ -175,6 +215,97 @@ export default function detailReducer(state=initialState, action) {
175 case SET_GOOESGROUP_Y: { 215 case SET_GOOESGROUP_Y: {
176 return state.set('goods_group_y', action.payload); 216 return state.set('goods_group_y', action.payload);
177 } 217 }
  218 + //获取资讯评论列表
  219 + case GET_COMMENTS_LIST_REQUEST: {
  220 + return state.setIn(['commentsList', 'isFetching'], true)
  221 + .setIn(['commentsList', 'error'], null);
  222 + }
  223 + case GET_COMMENTS_LIST_SUCCESS: {
  224 + return state.setIn(['commentsList', 'isFetching'], false)
  225 + .setIn(['commentsList', 'error'], null)
  226 + .setIn(['commentsList', 'page'], action.payload.page)
  227 + .setIn(['commentsList', 'total'], action.payload.total)
  228 + .setIn(['commentsList', 'total_page'], action.payload.total_page)
  229 + .setIn(['commentsList', 'data'], Immutable.fromJS(action.payload.data));
  230 + }
  231 + case GET_COMMENTS_LIST_FAILURE: {
  232 + return state.setIn(['commentsList', 'isFetching'], false)
  233 + .setIn(['commentsList', 'error'], action.payload);
  234 + }
  235 + //资讯添加评论
  236 + case ADD_COMMENTS_FOR_ARTIVLE_REQUEST: {
  237 + return state.setIn(['addComment', 'isFetching'], true)
  238 + .setIn(['addComment', 'message'], '')
  239 + .setIn(['addComment', 'error'], null);
  240 + }
  241 + case ADD_COMMENTS_FOR_ARTIVLE_SUCCESS: {
  242 + return state.setIn(['addComment', 'isFetching'], false)
  243 + .setIn(['addComment', 'error'], null)
  244 + .setIn(['addComment', 'data'], Immutable.fromJS(action.payload)
  245 + .setIn(['addComment', 'message'], '发表评论成功'));
  246 + }
  247 + case ADD_COMMENTS_FOR_ARTIVLE_FAILURE: {
  248 + return state.setIn(['addComment', 'isFetching'], false)
  249 + .setIn(['addComment', 'message'], '发表评论失败')
  250 + .setIn(['addComment', 'error'], action.payload);
  251 + }
  252 + case SET_PRAISE_FOR_COMMENTS: {
  253 + return state.setIn(['commentsList', 'data'], Immutable.fromJS(action.payload));
  254 + }
  255 + //资讯内容点赞
  256 + case ADD_PRAISE_FOR_COMMENTS_REQUEST: {
  257 + break;
  258 + }
  259 +
  260 + case ADD_PRAISE_FOR_COMMENTS_SUCCESS: {
  261 + break;
  262 + }
  263 + case ADD_PRAISE_FOR_COMMENTS_FAILURE: {
  264 + break;
  265 + }
  266 + //文章点赞Info
  267 + case GET_PRAISE_FOR_ARTIVLE_REQUEST: {
  268 + return state.setIn(['addPraiseInfo', 'isFetching'], true)
  269 + .setIn(['addPraiseInfo', 'error'], null);
  270 + }
  271 + case GET_PRAISE_FOR_ARTIVLE_SUCCESS: {
  272 + return state.setIn(['addPraiseInfo', 'isFetching'], false)
  273 + .setIn(['addPraiseInfo', 'browseNum'], action.payload.browseNum)
  274 + .setIn(['addPraiseInfo', 'id'], action.payload.id)
  275 + .setIn(['addPraiseInfo', 'isFavor'], action.payload.isFavor)
  276 + .setIn(['addPraiseInfo', 'isPraise'], action.payload.isPraise)
  277 + .setIn(['addPraiseInfo', 'praiseHeadIco'], Immutable.fromJS(action.payload.praiseHeadIco))
  278 + .setIn(['addPraiseInfo', 'praiseNum'], action.payload.praiseNum)
  279 + .setIn(['addPraiseInfo', 'error'], null);
  280 + }
  281 + case GET_PRAISE_FOR_ARTIVLE_FAILURE: {
  282 + return state.setIn(['addPraiseInfo', 'isFetching'], false)
  283 + .setIn(['addPraiseInfo', 'error'], action.payload);
  284 + }
  285 + case PRAISE_FOR_ARTIVLE_REQUEST:
  286 + {
  287 + return state.setIn(['addPraiseInfo', 'isPraise'], 'Y');
  288 + }
  289 + case PRAISE_FOR_ARTIVLE_SUCCESS:{break;}
  290 + case PRAISE_FOR_ARTIVLE_FAILURE:{break;}
  291 + case CANCEL_PRAISE_FOR_ARTIVLE_REQUEST:
  292 + {
  293 + return state.setIn(['addPraiseInfo', 'isPraise'], 'N');
  294 + }
  295 + case CANCEL_PRAISE_FOR_ARTIVLE_SUCCESS:{break;}
  296 + case CANCEL_PRAISE_FOR_ARTIVLE_FAILURE:{break;}
  297 + case ADD_FAVORITE_REQUEST:
  298 + {
  299 + return state.setIn(['addPraiseInfo', 'isFavor'], 'Y');
  300 + }
  301 + case ADD_FAVORITE_SUCCESS:{break;}
  302 + case ADD_FAVORITE_FAILURE:{break;}
  303 + case CANCEL_FAVORITE_REQUEST:
  304 + {
  305 + return state.setIn(['addPraiseInfo', 'isFavor'], 'N');
  306 + }
  307 + case CANCEL_FAVORITE_SUCCESS:{break;}
  308 + case CANCEL_FAVORITE_FAILURE:{break;}
178 } 309 }
179 310
180 return state; 311 return state;
@@ -145,4 +145,139 @@ export default class DetailService { @@ -145,4 +145,139 @@ export default class DetailService {
145 throw(error); 145 throw(error);
146 }); 146 });
147 } 147 }
  148 +
  149 +
  150 + async getCommentsList(article_id, page=1, limit=10) {
  151 + return await this.api.get({
  152 + url: '/guang/api/v1/comments/getList',
  153 + body: {
  154 + article_id,
  155 + page,
  156 + limit,
  157 + }
  158 + })
  159 + .then((json) => {
  160 + return json;
  161 + })
  162 + .catch((error) => {
  163 + throw(error);
  164 + });
  165 + }
  166 +
  167 + async addCommentsForArtivle(article_id, uid, content='', replyTo) {
  168 + return await this.api.get({
  169 + url: '/guang/api/v1/comments/add',
  170 + body: {
  171 + article_id,
  172 + content,
  173 + replyTo,
  174 + uid,
  175 + }
  176 + })
  177 + .then((json) => {
  178 + return json;
  179 + })
  180 + .catch((error) => {
  181 + throw(error);
  182 + });
  183 + }
  184 +
  185 + async addPraiseForComments(comment_id, praise, article_id) {
  186 + return await this.api.get({
  187 + url: '/guang/api/v2/comments/praise',
  188 + body: {
  189 + comment_id,
  190 + praise,
  191 + article_id,
  192 + }
  193 + })
  194 + .then((json) => {
  195 + return json;
  196 + })
  197 + .catch((error) => {
  198 + throw(error);
  199 + });
  200 + }
  201 +
  202 + //文章点赞info 用户uid 文章id
  203 + async getPraiseForArtivle(uid, id) {
  204 + return await this.api.get({
  205 + url: '/guang/api/v2/article/getArticlePraiseAndFavor',
  206 + body: {
  207 + uid,
  208 + id,
  209 + }
  210 + })
  211 + .then((json) => {
  212 + return json;
  213 + })
  214 + .catch((error) => {
  215 + throw(error);
  216 + });
  217 + }
  218 +
  219 + //点赞文章
  220 + async praiseForArtivle(article_id) {
  221 + return await this.api.get({
  222 + url: '/guang/api/v2/praise/setPraise',
  223 + body: {
  224 + article_id,
  225 + }
  226 + })
  227 + .then((json) => {
  228 + return json;
  229 + })
  230 + .catch((error) => {
  231 + throw(error);
  232 + });
  233 + }
  234 +
  235 + //取消点赞文章
  236 + async cancelPraiseForArtivle(article_id) {
  237 + return await this.api.get({
  238 + url: '/guang/api/v2/praise/cancel',
  239 + body: {
  240 + article_id,
  241 + }
  242 + })
  243 + .then((json) => {
  244 + return json;
  245 + })
  246 + .catch((error) => {
  247 + throw(error);
  248 + });
  249 + }
  250 +
  251 + //收藏文章
  252 + async addFavorite(uid, article_id) {
  253 + return await this.api.get({
  254 + url: '/guang/api/v1/favorite/setFavorite',
  255 + body: {
  256 + uid,
  257 + article_id,
  258 + }
  259 + })
  260 + .then((json) => {
  261 + return json;
  262 + })
  263 + .catch((error) => {
  264 + throw(error);
  265 + });
  266 + }
  267 + //取消收藏文章
  268 + async cancelFavorite(uid, article_id) {
  269 + return await this.api.get({
  270 + url: '/guang/api/v1/favorite/cancelFavorite',
  271 + body: {
  272 + uid,
  273 + article_id,
  274 + }
  275 + })
  276 + .then((json) => {
  277 + return json;
  278 + })
  279 + .catch((error) => {
  280 + throw(error);
  281 + });
  282 + }
148 } 283 }