forked from react-native-community/directory
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathscoring.tsx
230 lines (224 loc) · 8.94 KB
/
scoring.tsx
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
import React, { useContext } from 'react';
import { StyleSheet, View } from 'react-native';
import { H2, P, Headline, A, colors, darkColors } from '../common/styleguide';
import ContentContainer from '../components/ContentContainer';
import PopularityMark from '../components/Library/PopularityMark';
import Navigation from '../components/Navigation';
import CustomAppearanceContext from '../context/CustomAppearanceContext';
const ScoringCriterion = ({ children, headline, score = undefined }) => {
const { isDark } = useContext(CustomAppearanceContext);
const textStyle = {
color: isDark ? colors.gray2 : colors.black,
};
const borderStyle = {
borderColor: isDark ? darkColors.border : colors.gray2,
};
return (
<View style={[styles.criterionWrapper, borderStyle]}>
<Headline style={[styles.criterion, textStyle]}>
{headline}
{score && (
<Headline style={[styles.criterionScore, borderStyle]}>
{score > 0 ? '+' : ''}
{score}
</Headline>
)}
</Headline>
<P style={[styles.paragraph, { marginBottom: 0 }, textStyle]}>{children}</P>
</View>
);
};
const Scoring = () => {
const { isDark } = useContext(CustomAppearanceContext);
const textColorStyle = {
color: isDark ? colors.gray2 : colors.black,
};
const calloutStyle = {
color: isDark ? colors.gray2 : colors.black,
backgroundColor: isDark ? darkColors.warningLight : colors.warningLight,
borderLeftColor: isDark ? darkColors.warning : colors.warning,
};
return (
<>
<Navigation
title="Scoring"
description="What are the Directory Score and Popularity Score and how they are calculated?"
/>
<ContentContainer style={styles.container}>
<P style={[styles.paragraph, styles.callout, calloutStyle]}>
Directory scores are subjective and are based on data that's readily available on GitHub
and npm. They are not a perfect scores and may not reflect quality for your specific
needs. When evaluating libraries to include in your project, review the library yourself
to determine if it's a good fit.
</P>
<H2 style={[styles.subHeader, textColorStyle]}>Directory Score</H2>
<P style={[styles.paragraph, textColorStyle]}>
The Directory Score is the combination of multiple factors that relate to the quality of a
library. A library can earn value by exhibiting "good behavior criteria" and can lose
value by exhibiting "bad behavior criteria". These criteria and their corresponding
weights are detailed below. You can see the code this directory uses to create Directory
Scores{' '}
<A href="https://github.com/react-native-directory/website/blob/main/scripts/calculate-score.js">
here
</A>
.
</P>
<H2 style={[styles.subHeader, textColorStyle]}>Directory Score criteria</H2>
<P style={[styles.paragraph, textColorStyle]}>
The following criteria are used to calculate a library's Directory Score.
</P>
<ScoringCriterion headline="Very popular" score={40}>
Libraries with a combined popularity score of over 10,000 meet this criterion.
<br />
Combined popularity is measured by weighting and combining subscribers, forks, stars, and
download counts.
</ScoringCriterion>
<ScoringCriterion headline="Popular" score={10}>
Libraries with a combined popularity score of over 2,500 meet this criterion.
<br />
Combined popularity is measured by weighting and combining subscribers, forks, stars, and
download counts.
</ScoringCriterion>
<ScoringCriterion headline="Recommended" score={20}>
The maintainers of React Native Directory hand pick select recommended libraries.
</ScoringCriterion>
<ScoringCriterion headline="Recently updated" score={10}>
Libraries that have been updated in the last 30 days meet this criterion.
</ScoringCriterion>
<ScoringCriterion headline="Not updated recently" score={-10}>
Libraries that have not been updated in the last 180 days meet this criterion.
</ScoringCriterion>
<ScoringCriterion headline="Lots of open issues" score={-20}>
Libraries with more than 75 open issues meet this criterion.
</ScoringCriterion>
<ScoringCriterion headline="No license, unrecognized license or GPL license" score={-20}>
Libraries without a license, libraries with non-standard license or that include the GPL
license meet this criterion.
</ScoringCriterion>
<br />
<H2 style={[styles.subHeader, textColorStyle]}>Popularity Score</H2>
<P style={[styles.paragraph, textColorStyle]}>
The Popularity Score is the combination of multiple factors that relate to the download
count and quality of a library. A library gets the the base score from the Popularity Gain
criterion and can lose score by exhibiting one of bad criteria. These criteria and their
corresponding weights are detailed below. You can see the code this directory uses to
create Popularity Scores{' '}
<A href="https://github.com/react-native-directory/website/blob/main/scripts/calculate-score.js">
here
</A>
.
</P>
<P style={[styles.paragraph, textColorStyle]}>
There are five levels of popularity which depends on the package final Popularity Score:
<ul>
<li>
<PopularityMark markOnly library={{ popularity: 0.5001 }} />
 (final score > 50)
</li>
<li>
<PopularityMark markOnly library={{ popularity: 0.2501 }} />
 (final score > 25)
</li>
<li>
<PopularityMark markOnly library={{ popularity: 0.1001 }} />
 (final score > 10)
</li>
<li>
<PopularityMark markOnly library={{ popularity: 0.0001 }} />
 (final score > 0)
</li>
<li>
<PopularityMark markOnly library={{ popularity: 0 }} />
 (final score =< 0)
</li>
</ul>
</P>
<H2 style={[styles.subHeader, textColorStyle]}>Popularity Score criteria</H2>
<P style={[styles.paragraph, textColorStyle]}>
The following criteria are used to calculate a library's final Popularity Score.
</P>
<ScoringCriterion headline="Popularity Gain">
A base for the library score, it compares the monthly downloads count with weekly
downloads count and based on those values calculates a growth ratio for the package. Its
value range span can be quite wide, but most of the packages Popularity Gain value fits
within +/- 100 range. The formula used for calculating the score looks as following:
<br />
<View style={styles.formula}>
<code>
(lastWeekDownloads - Math.floor(monthlyDownloads / 4)) / monthlyDownloads) * 100
</code>
</View>
</ScoringCriterion>
<ScoringCriterion headline="Not many downloads" score={-45}>
Libraries with less than 250 monthly downloads meet this criterion.
</ScoringCriterion>
<ScoringCriterion headline="Not many followers" score={-10}>
Libraries with less than 25 starts on GitHub meet this criterion.
</ScoringCriterion>
<ScoringCriterion headline="No longer maintained" score={-25}>
Libraries that are marked with "unmaintained" flag meet this criterion.
</ScoringCriterion>
<ScoringCriterion headline="Very fresh package" score={-30}>
Libraries that first version was published less that 3 days ago meet this criterion.
</ScoringCriterion>
<br />
</ContentContainer>
</>
);
};
const styles = StyleSheet.create({
container: {
marginTop: 32,
paddingHorizontal: 16,
},
subHeader: {
marginTop: 16,
marginBottom: 20,
},
paragraph: {
fontSize: 17,
lineHeight: 29,
marginBottom: 17,
},
callout: {
borderLeftWidth: 8,
padding: 16,
marginBottom: 17,
},
criterionWrapper: {
paddingVertical: 16,
paddingHorizontal: 20,
borderWidth: 1,
borderStyle: 'solid',
borderRadius: 6,
marginBottom: 17,
},
criterion: {
fontSize: 18,
fontWeight: '600',
marginBottom: 8,
},
criterionScore: {
float: 'left',
marginRight: 16,
width: 44,
fontSize: 15,
fontWeight: '700',
padding: 1,
borderWidth: 1,
borderStyle: 'solid',
borderRadius: 4,
textAlign: 'center',
color: colors.primaryDark,
},
criterionScoreSymbol: {
position: 'relative',
top: 2,
left: 4,
},
formula: {
paddingHorizontal: 16,
marginTop: 12,
},
});
export default Scoring;