package Ġdk . nodes . n stack . lint Ċ Ċ import Ġcom . android . tools . lint . client . api . U Element Handler Ċ import Ġcom . android . tools . lint . detector . api . Context Ċ import Ġcom . android . tools . lint . detector . api . Detector Ċ import Ġcom . android . tools . lint . detector . api . Java Context Ċ import Ġcom . android . tools . lint . detector . api . Lint Fix Ċ import Ġcom . android . tools . lint . detector . api . Location Ċ import Ġcom . android . tools . lint . detector . api . Xml Context Ċ import Ġcom . android . xml . Android Manifest Ċ import Ġcom . intellij . psi . Psi Element Ċ import Ġcom . intellij . psi . Psi Method Ċ import Ġdk . nodes . n stack . lint . issues . App Open Missing Issue Ċ import Ġdk . nodes . n stack . lint . issues . N Stack Hard coded Issue Ċ import Ġdk . nodes . n stack . lint . issues . N Stack Test Issue Ċ import Ġdk . nodes . n stack . lint . issues . TextView Setter Issue Ċ import Ġorg . jetbrains . u ast . U Call Expression Ċ import Ġorg . jetbrains . u ast . U Element Ċ import Ġorg . jetbrains . u ast . UL iteral Expression Ċ import Ġorg . jetbrains . u ast . U Reference Expression Ċ import Ġorg . jetbrains . u ast . getValue If StringLiteral Ċ import Ġorg . w 3 c . dom . Element Ċ Ċ class ĠN Stack Issues Detector Ġ: ĊĠĠĠ ĠDetector (), ĊĠĠĠ ĠDetector . U ast Scanner , ĊĠĠĠ ĠDetector . Xml Scanner Ġ{ ĊĊĠĠĠ Ġprivate Ġvar Ġapp Open Called : ĠBoolean Ġ= Ġfalse ĊĠĠĠ Ġprivate Ġvar Ġn stack Init Location : ĠLocation ? Ġ= Ġnull ĊĊĠĠĠ Ġoverride Ġfun Ġbefore Check Root Project ( context : ĠContext ) Ġ{ ĊĠĠĠĠĠĠĠ Ġapp Open Called Ġ= Ġfalse ĊĠĠĠĠĠĠĠ Ġn stack Init Location Ġ= Ġnull ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoverride Ġfun Ġafter Check Root Project ( context : ĠContext ) Ġ{ ĊĠĠĠĠĠĠĠ Ġ// ĠWhen Ġall Ġmethods / classes Ġvisited Ġcheck Ġif Ġwe Ġrequired Ġmethods Ġwere Ġimplemented ĊĠĠĠĠĠĠĠ Ġn stack Init Location ?. let Ġ{ Ġinit Location Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠ Ġwhen Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ! app Open Called Ġ-> Ġcontext . report ( ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠApp Open Missing Issue . ISSUE , ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġinit Location , ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ" App Open Ġis Ġnot Ġcalled " ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoverride Ġfun Ġget Applicable Elements (): ĠCollection < String >? Ġ{ ĊĠĠĠĠĠĠĠ Ġreturn ĠlistOf ( TAG _ META _ DATA ) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoverride Ġfun Ġvisit Element ( context : ĠXml Context , Ġelement : ĠElement ) Ġ{ ĊĠĠĠĠĠĠĠ Ġ// ĠDon 't Ġcheck Ġlibrary Ġmanifest s ĊĠĠĠĠĠĠĠ Ġif Ġ( context . project Ġ!= Ġcontext . main Project Ġ|| ĊĠĠĠĠĠĠĠĠĠĠĠ Ġcontext . main Project . is Library ĊĠĠĠĠĠĠĠ Ġ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġreturn ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġif Ġ( TAG _ META _ DATA Ġ== Ġelement . nodeName ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġname Ġ= Ġelement . getAttribute NS ( ANDROID _ URI , ĠAndroid Manifest . ATTRIBUTE _ NAME ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( name Ġ== ĠN STACK _ API _ KEY Ġ|| Ġname Ġ== ĠN STACK _ APP _ ID Ġ|| Ġname Ġ== ĠN STACK _ ENV ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġvalue Ġ= Ġelement . getAttribute NS ( ANDROID _ URI , ĠAndroid Manifest . ATTRIBUTE _ VALUE ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġlast Path Segment Ġ= Ġname . split (". "). last () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ(! value . contains ("\ ${ ")) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġfix : ĠL int Fix Ġ= Ġfix (). set ( ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠAND ROID _ URI , ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠAndroid Manifest . ATTRIBUTE _ VALUE , ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ"\ ${ $ last Path Segment }" ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ). build () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcontext . report ( ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠN Stack Hard coded Issue . ISSUE , ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcontext . getLocation ( element ), ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ" You Ġcan Ġnot Ġhardcoded ĠN Stack ĠEnvironment Ġvariables ", ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġfix ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoverride Ġfun Ġget Applicable U ast Types (): ĠList < Class < out ĠU Element >> ? Ġ{ ĊĠĠĠĠĠĠĠ Ġreturn ĠlistOf < Class < out ĠU Element >>( UL iteral Expression :: class . java ) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoverride Ġfun Ġget Applicable Method Names (): ĠList < String >? Ġ{ ĊĠĠĠĠĠĠĠ Ġreturn ĠlistOf ( METHOD _ APP _ OPEN , ĠMETHOD _ SET _ TEXT , ĠMETHOD _ INIT ) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoverride Ġfun Ġvisit MethodCall ( context : ĠJava Context , Ġnode : ĠU Call Expression , Ġmethod : ĠPsi Method ) Ġ{ ĊĠĠĠĠĠĠĠ Ġval ĠmethodName Ġ= Ġnode . methodName ĊĠĠĠĠĠĠĠ Ġif Ġ( method . is From N Stack ( context . evaluator )) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġwhen Ġ( methodName ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠMETHOD _ SET _ TEXT Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġcaller Ġ= Ġnode . receiver Type Ġ?: Ġreturn ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( caller . canonical Text Ġ== Ġ" android . widget . TextView ") Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcontext . report ( ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠTextView Setter Issue . ISSUE , ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcontext . getLocation ( node ), ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ" Found Ġtext Ġview , Ġfix sss Ġsetter " ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠMETHOD _ APP _ OPEN Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġapp Open Called Ġ= Ġtrue ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠMETHOD _ INIT Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġn stack Init Location Ġ= Ġcontext . getLocation ( node ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoverride Ġfun Ġget Applicable Reference Names (): ĠList < String >? Ġ{ ĊĠĠĠĠĠĠĠ Ġreturn ĠlistOf () ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoverride Ġfun Ġvisit Reference ( ĊĠĠĠĠĠĠĠ Ġcontext : ĠJava Context , ĊĠĠĠĠĠĠĠ Ġreference : ĠU Reference Expression , ĊĠĠĠĠĠĠĠ Ġreferenced : ĠPsi Element ĊĠĠĠ Ġ) Ġ{ ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoverride Ġfun Ġcreate U ast Handler ( context : ĠJava Context ): ĠU Element Handler ? Ġ{ ĊĠĠĠĠĠĠĠ Ġ// ĠNote : ĠVisit ing ĠU AST Ġnodes Ġis Ġa Ġpretty Ġgeneral Ġpurpose Ġmechanism ; ĊĠĠĠĠĠĠĠ Ġ// ĠL int Ġhas Ġspecialized Ġsupport Ġto Ġdo Ġcommon Ġthings Ġlike Ġ" visit Ġevery Ġclass ĊĠĠĠĠĠĠĠ Ġ// Ġthat Ġextends Ġa Ġgiven Ġsuper Ġclass Ġor Ġimplements Ġa Ġgiven Ġinterface ", Ġand ĊĠĠĠĠĠĠĠ Ġ// Ġ" visit Ġevery Ġcall Ġsite Ġthat Ġcalls Ġa Ġmethod Ġby Ġa Ġgiven Ġname " Ġetc . ĊĠĠĠĠĠĠĠ Ġ// ĠTake Ġa Ġcareful Ġlook Ġat ĠU ast Scanner Ġand Ġthe Ġvarious Ġexisting Ġlint Ġcheck ĊĠĠĠĠĠĠĠ Ġ// Ġimplementations Ġbefore Ġdoing Ġthings Ġthe Ġ" hard Ġway ". ĊĠĠĠĠĠĠĠ Ġ// ĠAlso Ġbe Ġaware Ġof Ġcontext . get Java Evaluator () Ġwhich Ġprovides Ġa Ġlot Ġof ĊĠĠĠĠĠĠĠ Ġ// Ġutility Ġfunctionality . ĊĠĠĠĠĠĠĠ Ġreturn Ġobject Ġ: ĠU Element Handler () Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġoverride Ġfun Ġvisit Literal Expression ( expression : ĠU Literal Expression ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġstring Ġ= Ġexpression . getValue If StringLiteral () Ġ?: Ġreturn ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( string . contains (" lint ") Ġ&& Ġstring !!. matches (" .* \\ bl int \\ b .* ". to Regex ())) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcontext . report ( ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠN Stack Test Issue . ISSUE , Ġexpression , Ġcontext . getLocation ( expression ), ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ" This Ġcode Ġmentions Ġ` lint `: Ġ** Con grat ulations ** " ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġcompanion Ġobject Ġ{ ĊĠĠĠĠĠĠĠ Ġval ĠISS UES Ġ= ĠlistOf ( ĊĠĠĠĠĠĠĠĠĠĠĠ ĠN Stack Test Issue . ISSUE , ĊĠĠĠĠĠĠĠĠĠĠĠ ĠTextView Setter Issue . ISSUE , ĊĠĠĠĠĠĠĠĠĠĠĠ ĠApp Open Missing Issue . ISSUE , ĊĠĠĠĠĠĠĠĠĠĠĠ ĠN Stack Hard coded Issue . ISSUE ĊĠĠĠĠĠĠĠ Ġ) ĊĠĠĠĠĠĠĠ Ġ// ĠMethods ĊĠĠĠĠĠĠĠ Ġprivate Ġconst Ġval ĠMETHOD _ SET _ TEXT Ġ= Ġ" setText " ĊĠĠĠĠĠĠĠ Ġprivate Ġconst Ġval ĠMETHOD _ APP _ OPEN Ġ= Ġ" app Open " ĊĠĠĠĠĠĠĠ Ġprivate Ġconst Ġval ĠMETHOD _ INIT Ġ= Ġ" init " ĊĊĠĠĠĠĠĠĠ Ġ// ĠTAG S ĊĠĠĠĠĠĠĠ Ġprivate Ġconst Ġval ĠTAG _ META _ DATA Ġ= Ġ" meta - data " ĊĊĠĠĠĠĠĠĠ Ġprivate Ġconst Ġval ĠN STACK _ APP _ ID Ġ= Ġ" dk . nodes . n stack . appId " ĊĠĠĠĠĠĠĠ Ġprivate Ġconst Ġval ĠN STACK _ API _ KEY Ġ= Ġ" dk . nodes . n stack . apiKey " ĊĠĠĠĠĠĠĠ Ġprivate Ġconst Ġval ĠN STACK _ ENV Ġ= Ġ" dk . nodes . n stack . env " ĊĠĠĠĠĠĠĠ Ġprivate Ġconst Ġval ĠAND ROID _ URI Ġ= Ġ" http :// schemas . android . com / apk / res / android " ĊĠĠĠ Ġ} Ċ } Ċ