GitHub Access Token became invalid

It seems like the GitHub access token used for retrieving details about this repository from GitHub became invalid. This might prevent certain types of inspections from being run (in particular, everything related to pull requests).
Please ask an admin of your repository to re-new the access token on this website.

devto.*WebURL.UnmarshalJSON   A
last analyzed

Complexity

Conditions 2

Size

Total Lines 9
Code Lines 8

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 7
CRAP Score 2

Importance

Changes 0
Metric Value
cc 2
eloc 8
nop 1
dl 0
loc 9
rs 10
c 0
b 0
f 0
ccs 7
cts 7
cp 1
crap 2
1
package devto
2
3
import (
4
	"encoding/json"
5
	"fmt"
6
	"net/url"
7
	"strings"
8
	"time"
9
)
10
11
// User contains information about a devto account
12
type User struct {
13
	Name            string  `json:"name,omitempty"`
14
	Username        string  `json:"username,omitempty"`
15
	TwitterUsername string  `json:"twitter_username,omitempty"`
16
	GithubUsername  string  `json:"github_username,omitempty"`
17
	WebsiteURL      *WebURL `json:"website_url,omitempty"`
18
	ProfileImage    *WebURL `json:"profile_image,omitempty"`
19
	ProfileImage90  *WebURL `json:"profile_image_90,omitempty"`
20
}
21
22
// Organization describes a company or group that
23
// publishes content to devto.
24
type Organization struct {
25
	Name           string  `json:"name,omitempty"`
26
	Username       string  `json:"username,omitempty"`
27
	Slug           string  `json:"slug,omitempty"`
28
	ProfileImage   *WebURL `json:"profile_image,omitempty"`
29
	ProfileImage90 *WebURL `json:"profile_image_90,omitempty"`
30
}
31
32
// FlareTag represents an article's flare tag, if the article
33
// has one.
34
type FlareTag struct {
35
	Name         string `json:"name"`
36
	BGColorHex   string `json:"bg_color_hex"`
37
	TextColorHex string `json:"text_color_hex"`
38
}
39
40
// Tags are a group of topics related to an article
41
type Tags []string
42
43
// This deserialization logic is so that if a listed article
44
// originates from the /articles endpoint instead of
45
// /articles/me/*, its Published field is returned as true,
46
// since /articles exclusively returns articles that have been
47
// published.
48
type listedArticleJSON struct {
49
	TypeOf                 string        `json:"type_of,omitempty"`
50
	ID                     uint32        `json:"id,omitempty"`
51
	Title                  string        `json:"title,omitempty"`
52
	Description            string        `json:"description,omitempty"`
53
	CoverImage             *WebURL       `json:"cover_image,omitempty"`
54
	PublishedAt            *time.Time    `json:"published_at,omitempty"`
55
	PublishedTimestamp     string        `json:"published_timestamp,omitempty"`
56
	TagList                Tags          `json:"tag_list,omitempty"`
57
	Slug                   string        `json:"slug,omitempty"`
58
	Path                   string        `json:"path,omitempty"`
59
	URL                    *WebURL       `json:"url,omitempty"`
60
	CanonicalURL           *WebURL       `json:"canonical_url,omitempty"`
61
	CommentsCount          uint          `json:"comments_count,omitempty"`
62
	PositiveReactionsCount uint          `json:"positive_reactions_count,omitempty"`
63
	User                   User          `json:"user,omitempty"`
64
	Organization           *Organization `json:"organization,omitempty"`
65
	FlareTag               *FlareTag     `json:"flare_tag,omitempty"`
66
	BodyMarkdown           string        `json:"body_markdown,omitempty"`
67
	Published              *bool         `json:"published,omitempty"`
68
}
69
70
func (j *listedArticleJSON) listedArticle() ListedArticle {
71 1
	a := ListedArticle{
72
		TypeOf:                 j.TypeOf,
73
		ID:                     j.ID,
74
		Title:                  j.Title,
75
		Description:            j.Description,
76
		CoverImage:             j.CoverImage,
77
		PublishedAt:            j.PublishedAt,
78
		PublishedTimestamp:     j.PublishedTimestamp,
79
		TagList:                j.TagList,
80
		Slug:                   j.Slug,
81
		Path:                   j.Path,
82
		URL:                    j.URL,
83
		CanonicalURL:           j.CanonicalURL,
84
		CommentsCount:          j.CommentsCount,
85
		PositiveReactionsCount: j.PositiveReactionsCount,
86
		User:                   j.User,
87
		Organization:           j.Organization,
88
		FlareTag:               j.FlareTag,
89
		BodyMarkdown:           j.BodyMarkdown,
90
	}
91
92 1
	if j.Published != nil {
93 1
		a.Published = *j.Published
94
	} else {
95
		// "published" currently is included in the API
96
		// response for dev.to's /articles/me/* endpoints,
97
		// but not in /articles, so we are setting this
98
		// to true since /articles only returns articles
99
		// that are published.
100 1
		a.Published = true
101
	}
102 1
	return a
103
}
104
105
// ListedArticle represents an article returned from one of
106
// the list articles endpoints (/articles, /articles/me/*).
107
type ListedArticle struct {
108
	TypeOf                 string        `json:"type_of,omitempty"`
109
	ID                     uint32        `json:"id,omitempty"`
110
	Title                  string        `json:"title,omitempty"`
111
	Description            string        `json:"description,omitempty"`
112
	CoverImage             *WebURL       `json:"cover_image,omitempty"`
113
	PublishedAt            *time.Time    `json:"published_at,omitempty"`
114
	PublishedTimestamp     string        `json:"published_timestamp,omitempty"`
115
	TagList                Tags          `json:"tag_list,omitempty"`
116
	Slug                   string        `json:"slug,omitempty"`
117
	Path                   string        `json:"path,omitempty"`
118
	URL                    *WebURL       `json:"url,omitempty"`
119
	CanonicalURL           *WebURL       `json:"canonical_url,omitempty"`
120
	CommentsCount          uint          `json:"comments_count,omitempty"`
121
	PositiveReactionsCount uint          `json:"positive_reactions_count,omitempty"`
122
	User                   User          `json:"user,omitempty"`
123
	Organization           *Organization `json:"organization,omitempty"`
124
	FlareTag               *FlareTag     `json:"flare_tag,omitempty"`
125
	// Only present in "/articles/me/*" endpoints
126
	BodyMarkdown string `json:"body_markdown,omitempty"`
127
	Published    bool   `json:"published,omitempty"`
128
}
129
130
// UnmarshalJSON implements the JSON Unmarshaler interface.
131
func (a *ListedArticle) UnmarshalJSON(b []byte) error {
132 1
	var j listedArticleJSON
133 1
	if err := json.Unmarshal(b, &j); err != nil {
134
		return err
135
	}
136
137 1
	*a = j.listedArticle()
138 1
	return nil
139
}
140
141
// Article contains all the information related to a single
142
// information resource from devto.
143
type Article struct {
144
	TypeOf                 string     `json:"type_of,omitempty"`
145
	ID                     uint32     `json:"id,omitempty"`
146
	Title                  string     `json:"title,omitempty"`
147
	Description            string     `json:"description,omitempty"`
148
	CoverImage             *WebURL    `json:"cover_image,omitempty"`
149
	SocialImage            *WebURL    `json:"social_image,omitempty"`
150
	ReadablePublishDate    string     `json:"readable_publish_date"`
151
	Published              bool       `json:"published,omitempty"`
152
	PublishedAt            *time.Time `json:"published_at,omitempty"`
153
	CreatedAt              *time.Time `json:"created_at,omitempty"`
154
	EditedAt               *time.Time `json:"edited_at,omitempty"`
155
	CrossPostedAt          *time.Time `json:"crossposted_at,omitempty"`
156
	LastCommentAt          *time.Time `json:"last_comment_at,omitempty"`
157
	TagList                string     `json:"tag_list,omitempty"`
158
	Tags                   Tags       `json:"tags,omitempty"`
159
	Slug                   string     `json:"slug,omitempty"`
160
	Path                   *WebURL    `json:"path,omitempty"`
161
	URL                    *WebURL    `json:"url,omitempty"`
162
	CanonicalURL           *WebURL    `json:"canonical_url,omitempty"`
163
	CommentsCount          uint       `json:"comments_count,omitempty"`
164
	PositiveReactionsCount uint       `json:"positive_reactions_count,omitempty"`
165
	User                   User       `json:"user,omitempty"`
166
	BodyHTML               string     `json:"body_html,omitempty"`
167
	BodyMarkdown           string     `json:"body_markdown,omitempty"`
168
}
169
170
// ArticleUpdate represents an update to an article; it is
171
// used as the payload in POST and PUT requests for writing
172
// articles.
173
type ArticleUpdate struct {
174
	Title          string   `json:"title"`
175
	BodyMarkdown   string   `json:"body_markdown"`
176
	Published      bool     `json:"published"`
177
	Series         *string  `json:"series"`
178
	MainImage      string   `json:"main_image,omitempty"`
179
	CanonicalURL   string   `json:"canonical_url,omitempty"`
180
	Description    string   `json:"description,omitempty"`
181
	Tags           []string `json:"tags,omitempty"`
182
	OrganizationID int32    `json:"organization_id,omitempty"`
183
}
184
185
// ArticleListOptions holds the query values to pass as
186
// query string parameter to the Articles List action.
187
type ArticleListOptions struct {
188
	Tags     string `url:"tag,omitempty"`
189
	Username string `url:"username,omitempty"`
190
	State    string `url:"state,omitempty"`
191
	Top      string `url:"top,omitempty"`
192
	Page     int    `url:"page,omitempty"`
193
}
194
195
// MyArticlesOptions defines pagination options used as query
196
// params in the dev.to "list my articles" endpoints.
197
type MyArticlesOptions struct {
198
	Page    int `url:"page,omitempty"`
199
	PerPage int `url:"per_page,omitempty"`
200
}
201
202
// WebURL is a class embed to override default unmarshal
203
// behavior.
204
type WebURL struct {
205
	*url.URL
206
}
207
208
// UnmarshalJSON overrides the default unmarshal behaviour
209
// for URL
210
func (s *WebURL) UnmarshalJSON(b []byte) error {
211 1
	c := string(b)
212 1
	c = strings.Trim(c, "\"")
213 1
	uri, err := url.Parse(c)
214 1
	if err != nil {
215 1
		return err
216
	}
217 1
	s.URL = uri
218 1
	return nil
219
}
220
221
// ErrorResponse is an error returned from a dev.to API
222
// endpoint.
223
type ErrorResponse struct {
224
	ErrorMessage string `json:"error"`
225
	Status       int    `json:"status"`
226
}
227
228
func (e *ErrorResponse) Error() string {
229
	return fmt.Sprintf(`%d error: "%s"`, e.Status, e.ErrorMessage)
230
}
231