1+ /**
2+ * Determines whether a contributor is eligible to be assigned
3+ * a Beginner issue.
4+ *
5+ * ELIGIBILITY RULES:
6+ * - Team members bypass all checks
7+ * - Spam-listed users are never eligible
8+ * - Max open assignments enforced
9+ * - Must have completed at least N Good First Issues
10+ *
11+ * @param {Object } params
12+ * @param {import('@actions/github').GitHub } params.github
13+ * @param {string } params.owner
14+ * @param {string } params.repo
15+ * @param {string } params.username
16+ * @returns {Promise<{
17+ * eligible: boolean,
18+ * reason?: string,
19+ * context?: Object
20+ * }>}
21+ */
122const { isTeam } = require ( '../team/has-team' ) ;
223const { isOnSpamList } = require ( '../counts/is-on-spam-list' ) ;
3- const { hasCompletedGfi } = require ( '../counts/has-completed-n-01-gfi' ) ;
4- const { countOpenAssignedIssues } = require ( '../counts/count-opened-assigned-issues' ) ;
24+ const { hasCompletedGfi } =
25+ require ( '../counts/has-completed-n-01-gfi' ) ;
26+ const { countOpenAssignedIssues } =
27+ require ( '../counts/count-opened-assigned-issues' ) ;
528const REJECTION_REASONS = require ( './rejection-reasons' ) ;
629
30+ // ─────────────────────────────────────────────
31+ // Policy configuration
32+ // ─────────────────────────────────────────────
733const MAX_OPEN_ASSIGNED_ISSUES = 2 ;
834const REQUIRED_GFI_COUNT = 1 ;
935
@@ -19,39 +45,73 @@ const hasBeginnerEligibility = async ({
1945 username,
2046 } ) ;
2147
48+ // ─────────────────────────────────────────────
2249 // Team members bypass everything
50+ // ─────────────────────────────────────────────
2351 if ( await isTeam ( { github, owner, repo, username } ) ) {
52+ console . log ( '[has-beginner-eligibility] Bypass: team member' , {
53+ username,
54+ } ) ;
55+
2456 return { eligible : true } ;
2557 }
2658
59+ // ─────────────────────────────────────────────
2760 // Spam-listed users are never eligible
28- if ( await isOnSpamList ( { github, owner, repo, username } ) ) {
61+ // ─────────────────────────────────────────────
62+ const isSpamListed = await isOnSpamList ( {
63+ github,
64+ owner,
65+ repo,
66+ username,
67+ } ) ;
68+
69+ if ( isSpamListed ) {
70+ console . log ( '[has-beginner-eligibility] Rejected: spam listed' , {
71+ username,
72+ } ) ;
73+
2974 return {
3075 eligible : false ,
3176 reason : REJECTION_REASONS . SPAM ,
3277 } ;
3378 }
3479
80+ // ─────────────────────────────────────────────
3581 // Capacity check
82+ // ─────────────────────────────────────────────
3683 const openAssignedCount = await countOpenAssignedIssues ( {
3784 github,
3885 owner,
3986 repo,
4087 username,
4188 } ) ;
4289
90+ console . log ( '[has-beginner-eligibility] Capacity evaluation' , {
91+ username,
92+ openAssignedCount,
93+ maxAllowed : MAX_OPEN_ASSIGNED_ISSUES ,
94+ } ) ;
95+
4396 if ( openAssignedCount >= MAX_OPEN_ASSIGNED_ISSUES ) {
97+ console . log ( '[has-beginner-eligibility] Rejected: capacity exceeded' , {
98+ username,
99+ } ) ;
100+
44101 return {
45102 eligible : false ,
46103 reason : REJECTION_REASONS . CAPACITY ,
47104 context : {
48105 openAssignedCount,
49106 maxAllowed : MAX_OPEN_ASSIGNED_ISSUES ,
107+ isSpamListed : false ,
50108 } ,
51109 } ;
52110 }
53111
112+ // ─────────────────────────────────────────────
54113 // GFI prerequisite
114+ // ─────────────────────────────────────────────
55115 const hasRequiredGfi = await hasCompletedGfi ( {
56116 github,
57117 owner,
@@ -60,18 +120,34 @@ const hasBeginnerEligibility = async ({
60120 requiredCount : REQUIRED_GFI_COUNT ,
61121 } ) ;
62122
123+ console . log ( '[has-beginner-eligibility] GFI prerequisite' , {
124+ username,
125+ requiredGfiCount : REQUIRED_GFI_COUNT ,
126+ satisfied : hasRequiredGfi ,
127+ } ) ;
128+
63129 if ( ! hasRequiredGfi ) {
130+ console . log ( '[has-beginner-eligibility] Rejected: missing GFI' , {
131+ username,
132+ } ) ;
133+
64134 return {
65135 eligible : false ,
66136 reason : REJECTION_REASONS . MISSING_GFI ,
67137 context : {
68- completedGfiCount : 0 , // safe fallback
138+ requiredGfiCount : REQUIRED_GFI_COUNT ,
69139 } ,
70140 } ;
71141 }
72142
143+ // ─────────────────────────────────────────────
144+ // Eligible
145+ // ─────────────────────────────────────────────
146+ console . log ( '[has-beginner-eligibility] Eligible' , {
147+ username,
148+ } ) ;
149+
73150 return { eligible : true } ;
74151} ;
75152
76153module . exports = { hasBeginnerEligibility } ;
77-
0 commit comments